11

for ループと forEach のパフォーマンスを測定する jsperf の結果は信用できません。少なくとも私のマシンの chrome と firefox の結果は、jsperf で宣伝されているものとは完全に異なります。
http://jsperf.com/foreach-vs-loop (私のもの)
http://jsben.ch/#/BQhED (より一般的)
Ubuntu 11.10 を実行している私のラップトップでは、Firefox で次の結果が得られました。

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

残念ながら、Chrome は console.timeEnd() の結果を返しませんが、実行時間は同じで、Chrome の方が高速です。forEach は、Chrome の for ループよりもほぼ 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 の結果を信頼する必要がありますか? もちろん、私はブラウザで今ここで見ることができる実際の結果を信頼しています.

編集: @Blender との議論中に発見されたように、テスト シナリオは客観的ではありません。js オプティマイザーは forEach ループをアクションなしで最適化するように見えるため、実際のコードがある場合は実行時間が不明瞭になります。

4

3 に答える 3

10

あなたのコードをより公平になるように修正しました。見てもらえますか?

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% の生の数値計算ではなかったため、ベンチマークは一部のブラウザーによって不当に最適化されていました。

于 2012-03-17T02:40:35.597 に答える
5

これが実際のテストです: http://jsfiddle.net/ssSt5/57/ (複数回実行)

どうやら、それらは実質的に同じです。

したがって、実際の計算が行われているときは問題でfor vs forEachはありません。他の要因は、パフォーマンスにはるかに大きな影響を与えます。特にランタイムが最適化を適用した後。

于 2016-05-20T07:30:02.193 に答える
-1

このサイトでは、あらゆる種類の JavaScript ループ アプローチの結果を示していますhttp://www.jsbenchmarks.com/?anywhichway/loop/master/benchmark.js。ベンチマークを実行することを選択した場合、結果は、ベンチマークを実行するすべてのサイト訪問者の平均と比較されます。

于 2017-01-05T16:28:17.527 に答える