我偶然发现了这个jsperf

它测试编辑仅通过id或通过缓存选择器通过id访问的元素的html的相对性能。

编辑的元素深17层。

jsperf实际上报告不使用缓存的选择器更快。

<script src="http://code.jquery.com/jquery-latest.min.js"
        type="text/javascript"></script>
</script>
<div id="container"><div><div><div><div><div><div>
<div><div><div><div><div><div><div>
  <div>
    <div>
    </div>
    <div>
    </div>
    <div class="robotarm">
    </div>
    <div>
      <div id="robotarm">
      </div>
    </div>
    <div class="robotarm">
    </div>
    <div class="robotarm">
    </div>
    <div>
    </div>
  </div>
</div>
</div></div></div></div></div></div></div>
</div></div></div></div></div></div></div>

<div><div><div><div><div><div><div>
</div></div></div></div></div></div></div>
<div><div><div><div><div><div><div>
</div></div></div></div></div></div></div>
<div><div><div><div><div><div><div>
</div></div></div></div></div></div></div>
<div><div><div><div><div><div><div>
</div></div></div></div></div></div></div>
<script>
  Benchmark.prototype.setup = function() {
    function cached() {
      $div = $('#container');
      for (i = 0; i < 1000; i++){
        $div.find('#robotarm').html('foo');
      }
    }

    function raw() {
      for (i = 0; i < 1000; i++){
        $('#robotarm').html('foo');
      }
    }
  };
</script>


然而,表演是残酷的。为什么,为什么没有缓存的选择器更好呢?

最佳答案

关于该选择器没有任何“缓存”,命名是完全错误的。

在“原始”版本中,它们具有:

$('#robot-arm').html('foo');


将被优化为

$(document.getElementById("robot-arm")).html('foo');


但是“缓存”版本具有:

$div = $('#container');


然后

$div.find('#robot-arm').html('foo');


无法将其优化为document.getElementById调用,因为搜索仅限于#container元素。但是getElementById是从DOM中获取元素的最快方法。因此,它当然要慢一些。

“缓存”版本如下所示:

var $div = $("#robot-arm");


然后

$div.html('foo');


这(略)比测试的“原始”版本快:http://jsperf.com/using-id-selector-with-or-without-cached-scope/4

10-01 06:57
查看更多