类是否在现代浏览器中编入索引?

时间:2016-02-26 22:31:16

标签: javascript jquery google-chrome internet-explorer firefox

在过去的Web开发中,我总是试图在javascript中构建选择器时从id下载,之前在jQuery中,最近使用document.querySelector()/。querySelectorAll()。这是出于性能原因。我在这样的帖子(http://www.artzstudio.com/2009/04/jquery-performance-rules/#descend-from-id)中遵循建议。

例如:

$('#new-address-form input.address')

可能明显快于

$('.address')

即使页面上只有一个带有一类地址的元素。如果DOM中有很多不同的类,在某些浏览器中这可能会更快很多(我正在看你IE< 8)。

但是,从经验来看,今天似乎不再是这种情况了。任何人都可以向我指出一些文档或代码,对于开源浏览器,可以确认现代浏览器按类索引元素吗?

2 个答案:

答案 0 :(得分:1)

性能上存在差异,但除非您使用非常大的标记,否则它可能并不重要。

我设置了一个基准JS小提琴,它创建了20,000个div标签,每个标签嵌套10层深。然后尝试基于类随机选择一个,并再次基于具有后代类的ID。

我在这里对它进行了基准测试:https://jsfiddle.net/0wyLfnz8/14/

<强>结果
按ID选择,然后后代类在Chrome中平均为.018ms 按ID选择,然后后代类在IE中平均为39.33ms

仅按课程选择Chrome平均为12.178ms 在IE中,仅按类别选择平均为51.386ms

同样,这些结果以毫秒为单位,500次测试超过20,000个HTML元素

基准测试代码

$(document).ready(function() {
  var d = new Date();
  var st = d.getTime();
  var start = st;
  var et;
  var max = 20000;
  var numberOfTests = 500;
  var elementDepth = 10;
  for(var i = 1; i < max; i++) {
    //lets make a random class too
    r = Math.floor((Math.random() * 10) + 1);
    var depth = "";
    for(var j = 1; j<elementDepth;j++) {
      depth += '<div class="depth' + j + '"></div>'
    }
    $('body').append('<div id="d'+i+'">'+depth+'<div class="depth'+elementDepth+'"><div class="c'+i+' r'+r+'">Hello, I am div number '+i+'</div></div></div>');
  }
  d = new Date();
  var duration = d.getTime() - st;
  console.log('Generating divs took ' + (duration/1000) + ' seconds');

  idDuration = 0;
  idTests = 0;
  for(var i = 0; i < numberOfTests; i++) {
    //choose a random div to select
    r = Math.floor((Math.random() * max) + 1);
    d = new Date();
    st = d.getTime();
    var tagbyID = $('#d'+r+ '.c'+r);
    d = new Date();
    et = d.getTime();
    duration =  et - st;


    //console.log('Selecting by ID took ' + duration + ' milliseconds');
    idDuration += duration;
    idTests++;
  }
  console.log('---');

  classDuration = 0;
  classTests = 0;
  for(var i = 0; i < numberOfTests; i++) {
    //choose a random div to select
    r = Math.floor((Math.random() * max) + 1);
    d = new Date();
    st = d.getTime();
    var tagbyClass = $('.c'+r);
    d = new Date();
    et = et;
    duration = d.getTime() - st;
    //console.log('Selecting by class took ' + duration + ' milliseconds');
    classDuration += duration;
    classTests++;
  }
  console.log('---');
  d = new Date();
  console.log('total duration: ' + ((d.getTime() - start)/1000) + " seconds");
  console.log('---');
  console.log('Selecting by ID took '+idDuration+' milliseconds total over '+idTests+' tests.');
  console.log('Selecting by class took '+classDuration+' milliseconds total over '+classTests+' tests.');
  console.log('---');
  console.log('Average time for ID selection using $(\'#parentID .childClassName\') was: ' + (idDuration / idTests)+" milliseconds")
  console.log('Average time for class selection using $(\'.className\') was: ' + (classDuration / classTests)+" milliseconds")


})

答案 1 :(得分:0)

我可能已经回答了我自己的问题。我创建了一个jsperf,但我会重视更多的测试数据或改进。

http://jsperf.com/should-we-always-descend-by-an-id/6

编辑:在我的测试用例中,当你不从id下降时,jQuery实际上更快,但是明显的性能获胜者(跨浏览器)是 document.getElementsByClassName()