2012-03-17 13 views
9

forループに対するforループのパフォーマンスを測定するjsperfの結果は信頼できません。少なくとも私のマシンの結果のchromeとfirefoxは、jsperfで宣伝されているものとはまったく異なります。
http://jsperf.com/foreach-vs-loop私のラップトップ上で(私の)
http://jsben.ch/#/BQhED(より人気のある)
は私がFirefoxで以下の結果を持っているのUbuntu 11.10を実行している:forループ対jsperf結果の信頼性とjavascriptのそれぞれのパフォーマンス

for: total=1641 ms, avg=164.1 ms 
forEach: total=339 ms, avg=33.9 ms 

uname -a: 
Linux 3.0.0-16-generiC#29-Ubuntu SMP Tue Feb 14 12:48:51 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux 

残念ながら、クロム(console.timeEndの結果を返しません。 )しかし、Chromeの実行時間は同じで速いです。私は、forEachがChromeのループよりもほぼ10倍高速で、Firefoxでは3倍高速ということを観察しています。 Chromeの場合
私は約これらの実行中の時間を取得しています:

for: avg=80 ms 
forEach: avg=6 ms 

ここで私は、FirefoxとChromeのコンソールで実行したコードです。

var arr = []; 
for(var i = 0; i < 100000; i++) arr[i]=i; 

var numberOfRuns = 10; 

function time(name, f){ 
    console.time(name); 
    f(); 
    return console.timeEnd(name); 
} 

function runTest(name, f){ 
    var totalTime = 0; 
    for(var r = 0; r < numberOfRuns; r++) 
     totalTime += time(name,f); 
    return totalTime; 
} 

var forTime = runTest('for', function(){ 
    for(var j = 0; j < arr.length; j++) 
     arr[j];  
}); 
var forEachTime = runTest('forEach', function(){ 
    arr.forEach(function(v){v;}); 
}); 

console.log('for', {total:forTime, avg:forTime/numberOfRuns}); 
console.log('forEach', {total:forEachTime, avg:forEachTime/numberOfRuns}); 

100万件のテストの実行では、パフォーマンスの違いは同じです。私が何かを逃している場合は助言してください、私は観察している実際のものの代わりにjsperfの結果を信頼する必要がありますか?もちろん、今私のブラウザで見ることができる実際の結果を信頼しています。

EDIT:テストシナリオは、@Blenderとの議論で発見されたものではありません。 js optimizer optimezes forEachループのように見えます。実際のコードがあれば、実行時間を不明瞭にします。

+2

jsPerfは実際のテストを行います。それが使用するテストフレームワークは、あなたのより複雑なバージョンです。また、さまざまなブラウザのJSエンジンを考慮してください。 – Blender

+0

javascriptの開発者ではありませんが、私はインタプリタが 'v;'を何も最適化していないのに 'arr [j]'の値を探していると思います。 –

+0

jsperfのポイントは、相対的なパフォーマンスの違いを示すことです。あなたはまだ同じ相対的なパフォーマンスを見ている。あなたは何を正確に疑っていますか? – deceze

答えて

7

私はあなたのコードをより公平に変更しました。あなたはそれを見てみることができますか?

var arr = []; 
 
for (var i = 0; i < 100000; i++) arr[i] = i; 
 

 
var numberOfRuns = 100; 
 

 
function runTest(name, f) { 
 
    var totalTime = 0; 
 
    console.time(name); 
 

 
    for (var r = 0; r < numberOfRuns; r++) { 
 
     f(); 
 
    } 
 

 
    return console.timeEnd(name); 
 
} 
 

 
function testFunction(v) { 
 
    v; 
 
} 
 

 
var forTime = runTest('for', function() { 
 
    for (var j = 0; j < arr.length; j++) { 
 
     testFunction(arr[j]); 
 
    } 
 
}); 
 

 
var forEachTime = runTest('forEach', function() { 
 
    arr.forEach(testFunction); 
 
});

あなたのテストでは、クランチ100%生の数ではなかったので、ベンチマークは、一部のブラウザによって不当に最適化されていました。ここで

+0

ありがとうございました! –

+5

あなたのフィドルでは、ループが速いようです。しかし、開発者コンソールで同じコードを実行すると、毎回forEachが勝ちます。なぜそれが起こっているのだろうか? –

+1

@KushagraGour:手がかりがありません。質問する。 – Blender

3

は本当のテストです:http://jsfiddle.net/ssSt5/57/(それを複数回実行)

どうやら彼らは実質的に同じです。

実際の計算が行われているときは、for vs forEachは関係ありません。他の要素はパフォーマンスにはるかに大きな影響を与えます。特に実行時間の後に最適化が適用されました。

関連する問題