【发布时间】:2015-04-13 20:31:19
【问题描述】:
在使用.on() 增加委托事件绑定的特异性时是否会提高性能?
如何对此进行测试?
例如,第二个语句是否比第一个语句更高效:
$('.foo').on('mouseenter', ':has(.other)', function (e) {
console.log(e);
});
$('.bar').on('mouseenter', 'button:has(.other)', function (e) {
console.log(e);
});
$('.foo').on('mouseenter', ':has(.other)', function (e) {
console.log(e);
});
$('.bar').on('mouseenter', 'button:has(.other)', function (e) {
console.log(e);
});
.foo, .bar {
margin: 2em auto;
text-align: center;
}
<div class="foo">
<button type="button">Hello
<span class="other">World</span>
</button>
</div>
<div class="bar">
<button type="button">Hello
<span class="other">World</span>
</button>
</div>
我主要担心的是,使用委托侦听 mouseenter 事件会消耗性能,并且是否有办法测试此类事件处理程序的性能。
更新
我应该澄清一下,我并不想了解一般使用委托对性能的影响。我希望了解在用户交互期间使用mouseenter 委托对性能的影响(因为用户的鼠标在绑定元素中同时输入委托和非委托元素),以及是否通过使用更具体的选择器来提高性能用于委托。
我倾向于假设没有,因为每个事件都必须冒泡到绑定的元素,然后再根据委托选择器进行检查。
但是有没有办法对此进行测试?
【问题讨论】:
-
试过运行任何 jsperf 测试?
-
如果有的话,我认为第二个版本的性能可以忽略不计。无论如何,它们都会冒泡到祖先,而第二个版本需要检查节点类型以及类的存在。
-
我建议,一般来说,在
closest调用中使用:has(就像on在幕后所做的那样)会有糟糕的 性能.我会在选择器中测试button,然后在回调中使用.has()方法。 -
@gfullam 我确信委托是正确的选择。但是,我会尽力确保
:hasselector 不在您的选择器字符串中。它是一个 jQuery 选择器,而不是原生浏览器,因此非常慢。您正在树中的每个元素上使用它。如果你再做一个测试,比如button,然后使用.hasfunction 来测试那个元素,它会有更好的性能,因为它可以更好地使用浏览器的内置功能。 -
@gfullam 我意识到这一点。我的意思是你应该尝试将
:has从选择器中取出并在事件回调中进行测试;它会有更好的表现。请参阅these two examples:它们在功能上是等效的,但第一个具有更好的性能。
标签: jquery performance delegation event-delegation