Mootools选择器$或$$.哪个性能更高

Jam*_*ber 1 javascript mootools selector

我很好奇,浏览器查找哪个选择器会更快.我对一般而不是特定的浏览器感兴趣.

$('accountDetailsTable').getElements('.toggler')
Run Code Online (Sandbox Code Playgroud)

这将查找accountDetailsTable您正在使用document.getElementById('accountDetailsTable');,然后查找.toggler元素内部.

$$('.toggler')
Run Code Online (Sandbox Code Playgroud)

而这个将直接返回所有选择器.但最终他们都会给我相同的结果.

那么哪一个会更快?我该怎么测试呢?

Dim*_*off 5

选择器的性能在浏览器之间会有很大差异.例如.用querySelectorquerySelectorAll(QSA)与无.没有QSA时,getElementsByClassName有无.

选择器引擎需要做的工作量会有所不同.

你可以这样写.3种方法,而不仅仅是2:

1. $('accountDetailsTable').getElements('.toggler')

上面的解剖是:

  • 获取元素(1次调用).
  • 从元素原型调用方法getElements(或直接在旧IE中调用元素)
  • 查找与类选择器匹配的所有childNodes

这将在浏览器中保持一致,因为它获取根节点并从中调用方法.如果没有QSA,它将进入getElementsByClassName或走完所有childNodes并过滤该className属性,直到它有一个匹配列表.性能方面,在现代浏览器中这将更糟糕,因为它需要链,而方法3将是直接结果.

因为选择器如何在JS中工作,与CSS不同 - 它是从左到右,更多合格的选择器提高了性能,.toggler当有旧浏览器时有类似的意思,它不必要地考虑树中的每个DOM节点(文本除外)节点).在你可以的时候总是限定选择者,即div.togglera.toggler.

2. $$('.toggler')

  • 如果QSA是可用的,依赖于浏览器返回的东西(这里没有多余的黑客喜欢:not,或:contains:has!(反向组合程序).
  • 如果没有QSA,它将通过Slick解析器解析表达式,并且基本上内部降级为类似于上面的情况1.这里最大的区别是缺少上下文 - 它将针对整个文档运行,因为$$内部执行类似的操作,document.getElements('.toggler')因此需要考虑更多节点.始终将查询锚定到稳定的最常见节点.或者将其传递给查询字符串以进行限定,如案例3中所示

再次,这将通过使其更合格来改善性能,例如:

$$('a.toggler')

3. $$('#accountDetailsTable .toggler')

  • 与案例2类似,但当QSA可用时,它会更快.
  • 当QSA不存在时,它将针对#accountDetailsTable节点的上下文运行,因此它将优于情况2.

使这更合格将有所作为:

$$('#accountDetailsTable td.control > a.toggler')

大折扣:它取决于你的DOM有多大,找到并返回了多少匹配.在简单的DOM上,预期的性能顺序可能不同.

如今,选择器的性能优化越来越无关紧要.

SlickText框架比较的时代已经结束,应用程序性能与选择器速度没什么关系,或者你做错了什么.

如果你的工作正确,你就不需要经常选择元素.您可以缓存事物,重用,智能并将DOM查找减少到最少.

事件等可以通过智能事件委托附加,在适当的情况下,完全无需选择和添加事件到多个节点等 - 使用常识,不要挂在理论性能基准上.相反,使用分析器并测试您的实际应用程序,并查看您丢失时间/ CPU周期的位置.

你可以在一秒钟的时间内运行一个超过50000次的简单选择器.这是微基准测试,并不能测量APP,DOM,浏览器等内部的实际真实性能.

关于基准测试性能和过早优化的更多想法:http://www.youtube.com/watch?v = 65 -RbBwZQdU

小心

写的正确性和可读性第一.即使你可以通过做某事来获得额外的性能,如果它不是关键/一直重复使用,也不要以牺牲可读性为代价.像选择器.toggler,.new,.button等往往过于通用的,可以在DOM的不同部分在整个应用程序重复使用.您需要限定选择器以确保您的预期功能在移动到不同的页面/窗口小部件/ DOM时继续工作,并且您的项目会涌入新的开发人员.

只是我的两分钱,我知道你已经接受了答案.