3

hasOwnProperty()汚染される可能性があるため、オブジェクトのキーを反復処理するときに使用することになっていますObject.prototype。これは、プロトタイプの継承により、すべてのオブジェクトのキーも汚染します。

したがって、汚染しない場合は、 for-in ループを遅くObject.prototypeするスキップをスキップできるはずです。コードもシンプルになります。hasOwnProperty()

アイデア: 最初Object.prototypeに汚染されていないことを確認してから、使用しないでくださいhasOwnProperty()

Object.prototype汚染されていないことの確認は、次の関数によって行われます。これは、スクリプトの実行中に時折実行されるコード内の戦略的な場所で呼び出します (大量のデータを処理する前など)。この関数は、何か悪いことが行われた場合に私に警告するガードに過ぎませんObject.prototype:

/* jshint -W089 */  // http://jslinterrors.com/the-body-of-a-for-in-should-be-wrapped-in-an-if-statement/
var checkObjectPrototypeNotAugmented = function() {
    /* jshint unused:false */   // Because key is considered unused
    // Check if there is any enumerable property on Object.prototype:
    for(var key in Object.prototype) {
        throw new Error("Object.prototype has been augmented with keys: " + Object.prototype.keys());
    }
};

注:/* jshint -W089 */jshintが欠落についてhasOwnProperty()文句を言わないようにコメントを付けました。

質問: これは大丈夫ですか? 他に注意すべきことはありますか?それとも私が改善できることですか?


今いくつかのベンチマーク:

以下は、さまざまな数のプロパティを持つオブジェクトのゲインを示す 3 つの jsPerf ベンチマークです。

注:Object.prototypeオブジェクトのプロパティが反復されるたびに、チェックが実行されます。実際の状況では、テストを実行する必要があるのは 1 回だけです。つまり、ページ全体が読み込まれるときです (その後、スクリプトが誤って変更されていないことを確認するために時々Object.prototype)。したがって、実際の状況では、「参照」テストのパフォーマンスが得られます。しかし、これは、常にテストを実行している場合でも、高速のままであることを示しています。

興味深い結果:

  • どちらも使用しないhasOwnProperty()と、ブラウザに応じて同じ速度または高速になります
  • 1 つのプロパティにのみアクセスする場合でも、各 for-in ループの前にチェックObject.protoypeする方が、ブラウザーによってはhasOwnProperty()! (ただし、常にこのようにチェックすることはお勧めしませんObject.prototype

関連:Object.keys()一部のブラウザーでは大きなオブジェクトの使用がさらに高速になることもありますが、小さなオブジェクトの場合は遅くなる可能性もあります。しかし、を使用Object.keys()すると、ブラウザ >= IE 9 のみをサポートするか、またはIE <= 8Object.prototypeポリフィルObject.keys()で拡張する必要があります。したがって、古いブラウザとの互換性を確保するには、 または のいずれかを選択する必要がありますcheckObjectPrototypeNotAugmented()

4

0 に答える 0