素人がプログラミングを勉強していたブログ

プログラミング、セキュリティ、英語、Webなどのブログ since 2008

連絡先: twitter: @javascripter にどうぞ。

NodeListやHTMLCollectionに直接アクセスするより、一旦静的な配列にしたほうが速い

console.time('nodeList');
var elems = document.getElementsByTagName('*');
for(var i=0;i<1000;i++)
  for(var j=0;j<elems.length;j++)
    elems[j];
console.timeEnd('nodeList');

console.time('array');
var elems = Array.slice(document.getElementsByTagName('*'));
  for(var i=0;i<1000;i++)
    for(var j=0;j<elems.length;j++)
      elems[j];
console.timeEnd('array');

console.time('length');
var elems = document.getElementsByTagName('*');
for(var i=0;i<1000;i++)
  for(var j=0,length=elems.length;j<length;j++)
    elems[j];
console.timeEnd('length');

nodeList: 375ms
array: 78ms
length: 171ms

配列に直す処理が入るから遅くなりそうだけど、実際には一番速い。
NodeListの中身を削除する場合には、

var elems = document.body.childNodes;
while(elems.length) elems[0].parentNode.removeChild(elems[0]);

とするよりも、

var elems = Array.slice(document.body.childNodes);
for(var i=0;i<elems.length;i++)
  elems[i].parentNode.removeChild(elems[i]);

forEachを使って

var elems = Array.slice(document.body.childNodes);
elems.forEach(document.body.removeChild);

とすると、Cannot modify properties of a WrappedNativeというエラーになるので、関数で包まなきゃいけない。for文で普通にやるほうが楽。