我应该使用事件委托,以便在 table 单元格级别使用 JS 事件经济吗?
Should I use event delegation, to be economical with JS-events at i.e. table cell level?
如果我有一个 table,我想在其中对 table-cell 事件做出反应,是否最好将事件放在 table-element 上并处理特定于 cell 的事件?在 closest("td")
的帮助下进行事件,还是可以将事件放在 table 单元格上? (我说的是 tables 有大量的单元格,所有单元格都是可见的。)
// pseudo react-code
return (
<table onClick={handleCellClick}>
<tr>
<td>...</td><td>...</td><td>...</td><td>...</td>
</tr>
//...
</table>
)
或
// pseudo react-code
return (
<table>
<tr>
<td onClick={...}>...</td><td onClick={...}>...</td><td onClick={...}>...</td><td onClick={...}>...</td>
</tr>
//...
</table>
)
在不真正了解您的点击处理程序要做什么的情况下,这里有一个使用 event delegation, and data attributes 的示例,以展示如何识别单个单元格。
const { useState } = React;
function Example() {
function handleClick(e) {
if (e.target.matches('td')) {
const { dataset: { id } } = e.target;
console.log(id);
}
}
return (
<table onClick={handleClick}>
<tr>
<td data-id="1-1">1-1</td>
<td data-id="1-2">1-2</td>
<td data-id="1-3">1-3</td>
<td data-id="1-4">1-4</td>
</tr>
<tr>
<td data-id="2-1">2-1</td>
<td data-id="2-2">2-2</td>
<td data-id="2-3">2-3</td>
<td data-id="2-4">2-4</td>
</tr>
</table>
);
}
ReactDOM.render(
<Example />,
document.getElementById('react')
);
table { border-collapse: collapse; bordeR: 1px solid #565656; }
td { padding: 0.44em; border: 1px solid #dfdfdf; }
td:hover { cursor: pointer; background-color: #ffff00; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.2/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.2/umd/react-dom.production.min.js"></script>
<div id="react"></div>
由于您具体询问的是 React:No, you don't need to put only a single event handler at the table, React already does event delegation for you。所以使用 <td onClick={…}>
可能要简单得多,尤其是当你使用嵌套组件时。
结论是,在 vanilla JavaScript 中,事件委托是首选解决方案,以避免内存和性能问题。如果您使用的是 JavaScript 前端库,例如 React.js 或框架,例如 Ember、Angular,...您必须阅读文档并检查事件是如何管理的。在 React.js 的情况下,没有必要实现自定义事件委托,因为 React.js 为您做了这个优化。
如果我有一个 table,我想在其中对 table-cell 事件做出反应,是否最好将事件放在 table-element 上并处理特定于 cell 的事件?在 closest("td")
的帮助下进行事件,还是可以将事件放在 table 单元格上? (我说的是 tables 有大量的单元格,所有单元格都是可见的。)
// pseudo react-code
return (
<table onClick={handleCellClick}>
<tr>
<td>...</td><td>...</td><td>...</td><td>...</td>
</tr>
//...
</table>
)
或
// pseudo react-code
return (
<table>
<tr>
<td onClick={...}>...</td><td onClick={...}>...</td><td onClick={...}>...</td><td onClick={...}>...</td>
</tr>
//...
</table>
)
在不真正了解您的点击处理程序要做什么的情况下,这里有一个使用 event delegation, and data attributes 的示例,以展示如何识别单个单元格。
const { useState } = React;
function Example() {
function handleClick(e) {
if (e.target.matches('td')) {
const { dataset: { id } } = e.target;
console.log(id);
}
}
return (
<table onClick={handleClick}>
<tr>
<td data-id="1-1">1-1</td>
<td data-id="1-2">1-2</td>
<td data-id="1-3">1-3</td>
<td data-id="1-4">1-4</td>
</tr>
<tr>
<td data-id="2-1">2-1</td>
<td data-id="2-2">2-2</td>
<td data-id="2-3">2-3</td>
<td data-id="2-4">2-4</td>
</tr>
</table>
);
}
ReactDOM.render(
<Example />,
document.getElementById('react')
);
table { border-collapse: collapse; bordeR: 1px solid #565656; }
td { padding: 0.44em; border: 1px solid #dfdfdf; }
td:hover { cursor: pointer; background-color: #ffff00; }
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.2/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.2/umd/react-dom.production.min.js"></script>
<div id="react"></div>
由于您具体询问的是 React:No, you don't need to put only a single event handler at the table, React already does event delegation for you。所以使用 <td onClick={…}>
可能要简单得多,尤其是当你使用嵌套组件时。
结论是,在 vanilla JavaScript 中,事件委托是首选解决方案,以避免内存和性能问题。如果您使用的是 JavaScript 前端库,例如 React.js 或框架,例如 Ember、Angular,...您必须阅读文档并检查事件是如何管理的。在 React.js 的情况下,没有必要实现自定义事件委托,因为 React.js 为您做了这个优化。