興味深いことですが、ここでのちょっとしたテストでは、以前の仮定、つまり、jsPerf環境がスコープとスコープ チェーンのルックアップ自体に影響を与えるという仮説が裏付けられたようです。「方法」と「理由」については掘り下げませんでしたが、これは私の小さなテストスクリプトです。
var n1 = 12;
var add1 = function(n2){
return n1 + n2;
}
var add2 = (function(){
return function(n2){
return n1 + n2;
}
})();
var add3 = (function(){
var cn1 = n1;
return function(n2){
return cn1 + n2;
}
})();
var add4 = function( n2, n1 ) {
return n2 + n1;
}.bind(null, n1);
var tests = [add1, add2, add3, add4],
start, stop, loops;
tests.forEach(function( fnc ) {
loops = 100000;
start = Date.now();
while( loops-- ) {
fnc( 2 );
}
stop = Date.now();
console.info('Method ', fnc.name || fnc.toString(), ': ', stop - start, ' ms.');
});
FireFox 14 での結果は次のようになります。
メソッド add1: 570ms。
メソッド add2: 566ms。
メソッド add3: 414ms。
メソッド add4: 479ms。
最新の Chrome の結果:
メソッド add1: 199ms。
メソッド add2: 136ms。
メソッド add3: 85ms。
メソッド add4: 144ms。
これは間違いなくより合理的に見えます。クロージャ スコープ チェーンのルックアップは、より短いルックアップ チェーンがあるという事実のために、常に高速である必要があります。すべての最新のブラウザが通常、従来のスコープ チェーン ルックアップを実行しない場合でも、私はそれを認識しています。いずれにせよ、ブラウザーは自由な (または範囲外の) 変数に対して非常に巧妙なルックアップ テーブルを作成するため、すべての結果は少なくとも同じになるはずです。グローバル オブジェクト アクセス IMO を過度に最適化しても意味がありません。
お気づきのとおり、バインドされたメソッド用に 1 つの追加のテスト ケースを作成しました。