ホームページ ウェブフロントエンド jsチュートリアル 配列、配列コンストラクター、for in ループ、typeof、instanceOf_javascript 技巧

配列、配列コンストラクター、for in ループ、typeof、instanceOf_javascript 技巧

May 16, 2016 pm 06:02 PM
array constructor

注: JavaScript の配列は連想配列ではありません。 JavaScript には、キーと値の対応を管理するオブジェクトのみがあります。ただし、連想配列は順序を維持しますが、オブジェクトは順序を維持しません。

for in ループはプロトタイプ チェーン上のすべてのプロパティを列挙するため、これらのプロパティをフィルタリングする唯一の方法は `hasOwnProperty` 関数を使用することなので、通常の for ループよりも何倍も遅くなります。

反復
配列の走査で最高のパフォーマンスを達成するには、従来の for ループを使用することをお勧めします。

コードをコピー コードは次のとおりです:

var list = [1, 2, 3 , 4, 5, ... 100000000];
for(var i = 0, l = list.length; i console.log(list[i]); >}

上記のコードには、l = list.length によって配列の長さをキャッシュする処理があります。

長さは配列のプロパティですが、各ループで長さにアクセスするとパフォーマンスのオーバーヘッドが発生します。 最新の JavaScript エンジンがこれを最適化している可能性がありますが、コードがこれらの最新のエンジンで実行されるかどうかは保証できません。

実際、配列の長さをキャッシュしない方法は、キャッシュされたバージョンよりもはるかに遅くなります。

`length` プロパティ (`length` プロパティ)
length プロパティの getter メソッドは単純に配列の長さを返しますが、setter メソッドは配列を切り詰めます。

コードをコピーします コードは次のとおりです:
var foo = [1, 2, 3 , 4, 5, 6];
foo.length = 3; // [1, 2, 3]

foo; // [1, 2, 3]


翻訳者注: この時点で Firebug で foo の値を表示すると、 [1, 2, 3, unfined, undefined, unknown] になりますが、この結果は正確ではありませんChrome のコンソールで foo の結果を確認すると、次のようになることがわかります。 [1, 2, 3] 変数は JavaScript の変数であるため、変数の意味は異なります。上の 2 つの結果はまったく異なります。
// 翻訳者注: 確認するには、次のコードを実行して、シリアル番号 5 が foo に存在するかどうかを確認してみましょう。
5 in foo; // Firebug または Chrome のどちらでも false を返します。
foo[5] = unknown;
5 in foo; // Firebug または Chrome の場合、
は長さ A に設定されます。値を小さくすると配列が切り詰められますが、length プロパティを増やしても配列には影響しません。

結論 (結論として)
パフォーマンスを向上させるには、通常の for ループを使用し、配列の長さプロパティをキャッシュすることをお勧めします。 for in を使用して配列を反復処理することは、悪いコーディング方法とみなされ、エラーが発生し、パフォーマンスの問題が発生する傾向があります。

配列コンストラクター
配列のコンストラクターは引数の処理方法が少し曖昧であるため、配列の作成には配列のリテラル構文 [] を使用することを常にお勧めします。

[1, 2, 3]; // 結果: [1, 2, 3]
new Array(1, 2, 3); // 結果: [1, 2, 3]

[3]; // 結果: [3]
new Array(3) // 結果: []
new Array('3') // 結果: ['3']
翻訳者注: ここでの曖昧さは、配列の 2 つのコンストラクター構文を指します。 var arr1 = new Array(arrayLength); var arr2 = new Array(element0, element1, ..., elementN); / 翻訳者注: したがって、次のコードは非常に混乱するでしょう
new Array(3, 4, 5) // 結果: [3, 4, 5]
new Array(3) // 結果: [] 、この配列の長さは 3 です。
コンストラクターに渡されるパラメーターは 1 つだけであり (翻訳者注: new Array(3) の呼び出しメソッドを指します;)、このパラメーターは数値であるため、コンストラクターは空の値を返します。このパラメータに設定された長さプロパティを持つ配列。この時点では長さプロパティのみが設定され、実際の配列は生成されないことに注意することが重要です。翻訳者注: Firebug では [未定義、未定義、未定義] と表示されますが、これは実際には間違っています。前のセクションに詳細な分析があります。

var arr = new Array(3);
arr[1]; // 未定義
1 in arr; // 配列はまだ生成されていません
これが優先されます配列の設定よりも長さの属性は、for ループの問題を避けるために文字列をループする必要がある場合など、いくつかの状況でのみ役立ちます。

new Array(count 1).join(stringToRepeat);
// 翻訳者注: new Array(3).join('#') は "##" を返します
結論 (In結論)
新しい配列を作成するために配列コンストラクターを使用することは避けるべきです。配列のリテラル構文を使用することをお勧めします。これらはより短く、より簡潔であるため、コードの可読性が向上します。

for in ループ
in 演算子と同様に、for in ループもオブジェクトのプロパティを検索するときにプロトタイプ チェーン上のすべてのプロパティを走査します。

注: for in ループは、配列の length プロパティなど、enumerable が false に設定されているプロパティを反復しません。




コードをコピー
コードは次のとおりです:

// Object.prototype を変更します
Object.prototype.bar = 1;

var foo = {moo: 2};
for(var i in foo); 🎜>console.log(i); // bar と moo の 2 つの属性を出力します
}

for 自体の動作を変更することは不可能なので、フィルタリングする必要がありますループ本体に現れる予期しないプロパティ。これは、Object.prototype プロトタイプの `hasOwnProperty` 関数を通じて実行できます。

注: for in は常にプロトタイプ チェーン全体を走査するため、オブジェクトの継承レベルが深すぎるとパフォーマンスに影響します。

フィルタリングに `hasOwnProperty` を使用する

コードをコピー コードは次のとおりです:
// foo 変数は上記の例の変数です。
for(var i in foo) {
if (foo.hasOwnProperty(i)) {
console.log(i); 🎜>}
}


このバージョンのコードが唯一の正しい書き方です。 hasOwnPropertyを使用したので、今回はmooのみが出力されます。 hasOwnProperty が使用されていない場合、ネイティブ オブジェクト プロトタイプ (Object.prototype など) が拡張されるときにこのコードが壊れる可能性があります。

広く使用されているクラス ライブラリである Prototype は、ネイティブ JavaScript オブジェクトを拡張します。したがって、このクラス ライブラリがページに含まれている場合、hasOwnProperty フィルターを使用しない for in ループでは必然的に問題が発生します。

ベスト プラクティス
常に hasOwnProperty を使用することをお勧めします。コードが実行されている環境について仮定を立てたり、ネイティブ オブジェクトが拡張されているかどうかを仮定したりしないでください。

typeof 演算子
typeof 演算子 (`instanceof` とともに) は、おそらく JavaScript の最大の設計上の欠陥です。なぜなら、typeof 演算子から望ましい結果を得るのはほぼ不可能だからです。

instanceof には非常に少数のアプリケーション シナリオがありますが、typeof には実用的なアプリケーションが 1 つだけあります (翻訳者注: この実用的なアプリケーションは、オブジェクトが定義されているか、値が割り当てられているかを検出するために使用されます)。オブジェクトのタイプを確認するためには使用されません。

注: typeof は typeof(obj) などの関数構文で呼び出すこともできますが、これは関数呼び出しではありません。これら 2 つの括弧は式の値を計算するためにのみ使用され、戻り値は typeof 演算子のオペランドとして使用されます。実際には typeof という名前の関数はありません。


JavaScript 型テーブル
値クラス型 ---------------------- - ------------------
"foo" String string
new String("foo") String オブジェクト
1.2 Number 数値
new Number (1.2 ) Number オブジェクト
true Boolean boolean
new Boolean(true) Boolean オブジェクト
new Date() Date オブジェクト
new Error() Error オブジェクト
[1,2,3] 配列object
new Array(1, 2, 3) 配列オブジェクト
new Function("") 関数 function
/abc/g RegExp オブジェクト (Nitro/V8 の関数)
new RegExp("meow ") RegExp オブジェクト (Nitro/V8 の関数)
{} Object オブジェクト
new Object() Object オブジェクト
上の表の Type 列は、typeof 演算子の演算結果を表します。ご覧のとおり、ほとんどの場合、この値は「オブジェクト」を返します。

クラス オブジェクトの内部プロパティ [[Class]] の値を表す列。

JavaScript 標準ドキュメントでは次のように定義されています: [[Class]] 値は次の文字列の 1 つだけです: Arguments、Array、Boolean、Date、Error、Function、JSON、Math、Number、Object、RegExp、String .

オブジェクトの [[Class]] を取得するには、Object.prototype で定義されたメソッド toString を使用する必要があります。

オブジェクトのクラス (オブジェクトのクラス)
JavaScript 標準ドキュメントでは、[[Class]] 値を取得する 1 つの方法のみが提供されており、それは Object.prototype.toString を使用することです。


function is(type, obj) {
var clas = Object.prototype.toString.call(obj).slice(8, -1);
return obj !== 未定義 && obj !== null && clas === type;

is('String', 'test'); // true
is('String', new String('test')); // true


上記の例では、Object.prototype.toString メソッドが呼び出され、[[Class]] 値を取得する必要があるオブジェクトに設定されます。
翻訳者注: Object.prototype.toString は標準形式の文字列を返すため、上記の例では、以下に示すように、スライスを介して指定された位置で文字列をインターセプトできます。 >
コードをコピーします


コードは次のとおりです:
Object.prototype.toString.call([]) // "[オブジェクト配列]" Object.prototype.toString.call({}) // "[オブジェクト オブジェクト]" Object.prototype.toString.call(2) // "[オブジェクト番号]"
ES5 のヒント: ECMAScript 5 では、便宜上、Object.prototype.toString メソッドが null および未定義で呼び出され、その戻り値が Object から Null および Unknown に変更されます。

翻訳者注: 以下に示すように、この変更は IE8 および Firefox 4 で確認できます:
コードをコピーコードは次のとおりです。

// IE8
Object.prototype.toString.call(null) // "[object Object]"
Object.prototype.toString.call ( unknown) // "[object Object]"

// Firefox 4
Object.prototype.toString.call(null) // "[object Null]"
Object.prototype.toString 。 call(unknown) // "[object Unknown]"
未定義変数のテスト
typeof foo !== 'unknown'

上記のコードは、foo が定義されているかどうかを検出します。定義されていない場合、直接使用すると、ReferenceError 例外が発生します。 typeof が役立つのはここだけです。

結論
オブジェクトの型を検出するには、Object.prototype.toString メソッドを使用することを強くお勧めします。これが唯一信頼できる方法だからです。上の表に示すように、typeof の一部の戻り値は標準ドキュメントで定義されていないため、エンジンの実装が異なると異なる場合があります。

変数が定義されているかどうかを確認する場合を除き、typeof 演算子の使用は避けるべきです。

instanceof 演算子
instanceof 演算子は、2 つのオペランドのコンストラクターを比較するために使用されます。カスタム オブジェクトを比較する場合にのみ意味があります。組み込み型の比較に使用すると、typeof 演算子と同じくらい役に立たなくなります。

カスタム オブジェクトの比較
コードをコピー コードは次のとおりです:

function Foo() {}
function Bar() {}
Bar.prototype = new Foo();

new Bar() instanceof Bar; // true
new Bar() instanceof Foo; // true

// Foo コンストラクターのインスタンスではなく、Bar.prototype を関数 Foo 自体に設定するだけの場合
Bar.prototype =
new Bar; )instanceof Foo; // false
`instanceof` ネイティブ型で `instanceof` を使用する)
new String('foo')instanceof String; // true
new String('foo ')instanceof Object; // true

'foo'instanceof String; // false
'foo'instanceof Object; // false

注意すべき点は、instanceof の場合です。異なる JavaScript コンテキスト (ブラウザー内の異なるドキュメント構造など) に属するオブジェクトを比較する場合、それらのコンストラクターは同じオブジェクトではないためです。

結論 instanceof 演算子は、同じ JavaScript コンテキストからのカスタム オブジェクトを比較する場合にのみ使用してください。 「typeof」演算子の場合と同様、他の使用は避けてください。
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。

ホットAIツール

Undresser.AI Undress

Undresser.AI Undress

リアルなヌード写真を作成する AI 搭載アプリ

AI Clothes Remover

AI Clothes Remover

写真から衣服を削除するオンライン AI ツール。

Undress AI Tool

Undress AI Tool

脱衣画像を無料で

Clothoff.io

Clothoff.io

AI衣類リムーバー

AI Hentai Generator

AI Hentai Generator

AIヘンタイを無料で生成します。

ホットツール

メモ帳++7.3.1

メモ帳++7.3.1

使いやすく無料のコードエディター

SublimeText3 中国語版

SublimeText3 中国語版

中国語版、とても使いやすい

ゼンドスタジオ 13.0.1

ゼンドスタジオ 13.0.1

強力な PHP 統合開発環境

ドリームウィーバー CS6

ドリームウィーバー CS6

ビジュアル Web 開発ツール

SublimeText3 Mac版

SublimeText3 Mac版

神レベルのコード編集ソフト(SublimeText3)

C# の Array.Sort 関数を使用して配列を並べ替える C# の Array.Sort 関数を使用して配列を並べ替える Nov 18, 2023 am 10:37 AM

タイトル: Array.Sort 関数を使用して C# で配列を並べ替える例 本文: C# では、配列は一般的に使用されるデータ構造であり、多くの場合、配列を並べ替える必要があります。 C# には Array クラスが用意されており、このクラスには配列を簡単に並べ替えるための Sort メソッドがあります。この記事では、C# で Array.Sort 関数を使用して配列を並べ替える方法を示し、具体的なコード例を示します。まず、Array.Sort 関数の基本的な使用法を理解する必要があります。 Array.So

PHP で array_combine 関数を使用して 2 つの配列を結合して連想配列にする方法 PHP で array_combine 関数を使用して 2 つの配列を結合して連想配列にする方法 Jun 26, 2023 pm 01:41 PM

PHP には、配列操作をより便利かつ高速にする強力な配列関数が多数あります。 2 つの配列を結合して連想配列にする必要がある場合、PHP の array_combine 関数を使用してこの操作を実行できます。この関数は、実際には、ある配列のキーを別の配列の値として新しい連想配列に結合するために使用されます。次に、PHP の array_combine 関数を使用して 2 つの配列を結合して連想配列にする方法を説明します。 array_comb について学ぶ

PHPのarray_merge_recursive()関数を使用するシンプルで明確な方法 PHPのarray_merge_recursive()関数を使用するシンプルで明確な方法 Jun 27, 2023 pm 01:48 PM

PHP でプログラミングする場合、多くの場合、配列をマージする必要があります。 PHP には、配列のマージを完了するための array_merge() 関数が用意されていますが、配列内に同じキーが存在する場合、この関数は元の値を上書きします。この問題を解決するために、PHP は配列をマージして同じキーの値を保持できる array_merge_recursive() 関数を言語で提供し、プログラム設計をより柔軟にします。配列マージ

PHPのarray_fill()関数の使い方の詳しい説明 PHPのarray_fill()関数の使い方の詳しい説明 Jun 27, 2023 am 08:42 AM

PHP プログラミングにおいて、配列は大量のデータを簡単に処理できる非常に重要なデータ構造です。 PHP は配列関連の関数を多数提供しており、array_fill() はその 1 つです。この記事では、array_fill() 関数の使い方と実際の応用におけるヒントを詳しく紹介します。 1. array_fill() 関数の概要 array_fill() 関数の機能は、同じ値で構成される指定された長さの配列を作成することです。具体的には、この関数の構文は次のとおりです。

PHP8 のコンストラクター プロパティ プロモーションを通じてクラスのコンストラクターを簡素化するにはどうすればよいですか? PHP8 のコンストラクター プロパティ プロモーションを通じてクラスのコンストラクターを簡素化するにはどうすればよいですか? Oct 18, 2023 am 10:51 AM

PHP8 の ConstructorPropertyPromotion を通じてクラスのコンストラクターを簡素化するにはどうすればよいですか? PHP8 では、ConstructorPropertyPromotion 機能が導入され、クラス コンストラクターの作成がより簡潔かつ効率的になりました。この機能により、冗長なコードが削減され、コードの可読性と保守性が向上します。この記事ではConstructorPropertyProについて詳しく紹介します

Java での ArrayIndexOutOfBoundsException の一般的な原因は何ですか? Java での ArrayIndexOutOfBoundsException の一般的な原因は何ですか? Jun 24, 2023 pm 10:39 PM

Java は、さまざまな開発分野で広く使用されている非常に強力なプログラミング言語です。ただし、Java プログラミング中に、開発者は ArrayIndexOutOfBoundsException 例外に遭遇することがよくあります。では、この異常の一般的な原因は何でしょうか? ArrayIndexOutOfBoundsException は、Java の一般的なランタイム例外です。これは、データにアクセスするときに、配列の添字が配列の範囲を超えていることを意味します。一般的な理由には次のようなものがあります。

PHP の array_change_key_case() 関数の使用方法の概要 PHP の array_change_key_case() 関数の使用方法の概要 Jun 27, 2023 am 10:43 AM

PHP プログラミングでは、配列は頻繁に使用されるデータ型です。 array_change_key_case() 関数など、多数の配列操作関数もあります。この関数は、配列内のキー名の大文字と小文字を変換して、データ処理を容易にすることができます。この記事では、PHP での array_change_key_case() 関数の使用方法を紹介します。 1. 関数の構文とパラメータ array_change_ke

Python で Array モジュールを使用する方法 Python で Array モジュールを使用する方法 May 01, 2023 am 09:13 AM

Python の配列モジュールは事前定義された配列であるため、標準のリストよりもメモリ内で使用するスペースがはるかに少なく、追加、削除、インデックス付け、スライスなどの要素レベルの操作を高速に実行することもできます。さらに、配列内のすべての要素は同じ型であるため、平均値、最大値、最小値の計算など、配列が提供する効率的な数値演算関数を使用できます。さらに、配列モジュールは、配列オブジェクトのバイナリ ファイルへの直接の書き込みと読み取りもサポートしているため、大量の数値データを処理する際の効率が向上します。したがって、大量の同種データを処理する必要がある場合は、Python の配列モジュールを使用してコードの実行効率を最適化することを検討してください。配列モジュールを使用するには、まず次のことを行う必要があります。

See all articles