A Day in the Life

2009-03-16

今日の tablog

MDCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC

f:id:secondlife:20090316224902p:image

画像周りの速度メモ

キャッシュにのってたり、ネットワーク転送速度を無視できる画像の使い回しは data スキームより、http な URI のほうが 1.2倍( Firefox 3.0.7, Safari 3.2.1 )ほど速い。Opera はもうちょっと速い。String の読み込みと base64 のデコードが発生するからかな。base64 化してない data スキームは調べてない。

// var data = 'data:image/gif;base64,R0lGODlhCwAKAMQVAPi+Sv3FVvjHZvi9R/i3OfjDWv7KYva8Rf/Oa/e5Pfi9SfvATPi7Qv3HWvvCUP7Naf3GWf/MafazK/i4NvfBVf///wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACH5BAEAABUALAAAAAALAAoAAAUvYCWK1GiO0mlSSalWVOOS0yRBCCTVrmI8QIjjBIgYD6pFYBAonCYEQUWwMzGIohAAOw==';
var data = 'http://s.hatena.ne.jp/images/star.gif';

var container = document.getElementById('image-container');
var now = new Date*1;
for (var i = 0; i < 10000; i++) {
  // var img = document.createElement('img');
  var img = new Image();
  img.src = data;
  container.appendChild(img);
}
document.title = (new Date*1) - now;

Firefox は画像を作って突っ込む処理が webkit/opera に比べてやたらと遅いよ。

画像 Element を作って cloneNode(false) で使い回す

var img = new Image();
img.src = data;
for (var i = 0; i < 10000; i++) {
  container.appendChild(img.cloneNode(false));
}
for (var i = 0; i < 10000; i++) {
  var img = new Image();
  img.src = data;
  container.appendChild(img);
}

cloneNode のほうが 1割ぐらい速い。safari 3.2.1 だと2割ぐらい速い。

DocumentFragment を使う

var fragment = document.createDocumentFragment();
var img = new Image();
img.src = data;
for (var i = 0; i < 10000; i++) {
  fragment.appendChild(img.cloneNode(false));
}
container.appendChild(fragment);
document.title = (new Date*1) - now;

Fx で 2.5割ぐらい速い。Safari だと 1割ぐらい速い。

一時的に、画像が格納される要素を非表示にする

style.display を弄る

container.style.display = 'none';
container.appendChild(fragment);
container.style.display = 'block';

変化無し。タイミングによっては遅くなる。

parentNode から removeChild しておく

var fragment = document.createDocumentFragment();
var img = new Image();
img.src = data;
for (var i = 0; i < 10000; i++) {
  fragment.appendChild(img.cloneNode(false));
}
var parentRef = container.parentNode;
parentRef.removeChild(container);
container.appendChild(fragment);
parentRef.appendChild(container);

6 割ぐらい速くなった。しかし上記コードは、parentRef だけしか参照していないし、ノードの場所も記録してないので、使いやすくするため単純にこうすると遅くて使い物にならない。

for (var i = 0; i < 10000; i++) {
 var parentRef = container.parentNode;
 parentRef.removeChild(container);
 container.appendChild(img.cloneNode(false));
 parentRef.appendChild(container);
}

うーん。こ。

記事の一覧 >