例如:
HTML:
<body>
<div id="div_1"></div>
<div id="div_2"></div>
</body>
js(1):
document.getElementById("div_1").addEventListener("click",function(){
// 对div_1的操作
});
document.getElementById("div_2").addEventListener("click",function(){
// 对div_2的操作
});
若利用冒泡。以上js(1)的实现也可以写成
js(2):
document.body.addEventListener("click",function(e){
if(e.target.id == "div_1"){
// 对div_1的操作
}else if(e.target.id == "div_2"){
// 对div_2的操作
}
});
对于js(1)和js(2),实际使用是否有差异,若有,两者哪个更优?
题主真是一个爱思考的好少年,描述提到的冒泡捕获事件的方法,实际上就是所谓「事件委托」。
要讨论对单个节点的事件绑定和事件委托哪个更优,那必须得说明一下事件委托在解决什么问题。
首先,它绝不仅仅是在事件监听时为大家提供了一个新的选项。举个栗子,如果需要对选择器
.enabled
对应的所有元素绑定事件处理函数foo()
, 经典的做法便是不得不一个个遍历所有节点并绑定事件处理函数,如果解除绑定也是同样。为了保存每一个元素的事件绑定而带来的内存开销和遍历DOM造成的性能损失且不说,为新增加或者移除的元素添加或者移除绑定本身就是一件非常头疼的事情。而事件委托却没有此问题,无论是添加元素或者删除元素,无论是删除绑定还是新增绑定,开销都非常小。说到性能,如果还在担心冒泡本身是否会造成更大的开销,那不妨考虑一下,为每一个元素添加绑定的方法,难到就不会造成冒泡吗?换句话说,绑定与否跟冒泡与否是否有必然联系呢?当然,使用何种技术本身是需要经过考量的,相信了解了细节的题主会处理好两种方案的关系。
题主如果有兴趣,可以看看 jQuery 事件委托的实现: https://github.com/jquery/jquery/blob/master/src/event.js#L794