また、開始する前に、この情報がJavaScriptにのみ適用されることを明確にします。 つまり、JavaScript言語の擬似配列について説明します。
擬似配列(配列のようなオブジェクトまたはコレクション)とは何ですか?
擬似配列は、構造的に配列に類似したオブジェクトです。 つまり、数値プロパティ(インデックス)と
length
プロパティがあります。
例:
{0: ' 1', 1: ' 2', 2: ' 3', length: 3};
擬似配列は配列とどう違うのですか?
擬似配列と配列の主な違いは、プロトタイプの継承、つまり
__proto__
プロパティです。
配列のプロパティを見ると、 Arrayオブジェクトのプロトタイプを継承していることがわかります。 つまり、 Array.prototypeオブジェクトにあるすべてのプロパティは、どの配列でも使用できます。 擬似配列のプロパティを見ると、他のプロパティとともに他のオブジェクトのプロトタイプを継承していることがわかります。
擬似配列に関連するオブジェクトタイプのリスト
擬似配列は、さまざまなオブジェクトのプロトタイプを継承できます。 オブジェクトタイプの小さなリスト-疑似配列を次に示します。
-
DOMTokenList
-
NamedNodeMap
-
DOMStringMap
-
HTMLCollection
-
NodeList
-
HTMLAllCollection
-
StyleSheetList
-
DOMStringList
-
HTMLMapElement
-
CSSRuleList
これは、50を超えるタイプを持つ疑似配列タイプの完全なリストのごく一部です。 記事の次の段落はこれから続きます。
通常のオブジェクトと擬似配列を区別する方法は?
3日間、さまざまな記事を読みながらこの質問を整理しました。その結果、条件を1つだけ作成しました。オブジェクトが擬似配列の場合、
length
プロパティが必要です。これは整数で、ゼロ以上でなければなりません。
Number.isInteger(Number(object.length)) && Number(object.length) >= 0
次のアイテムを折りたたんでこの状態を作りました。
- 数値のプロパティと等しくすることはできません。それらを指定しない場合、これらが等しくないことを意味しないためです。 それらは単に
undefined
と等しくなります - 擬似配列のタイプを見ると、それらのタイプに
Collection
、Map
またはList
という単語が含まれていることがわかりました。 しかし、疑似配列は通常のオブジェクトのタイプを持つことができるため、この考えはすぐに解消されました-Object、
そして、普通の配列でさえこの項目に該当しないため、一般にこれは愚かです。 - 非数値プロパティを配列に含めることができるため、非数値プロパティを同等にすることもできません。
しかし、JavaScriptは私の状態が酷すぎると「言った」。 疑似配列を配列に変換するためのオプションを分析すると、JavaScriptは、
length
プロパティがゼロ以上の数値に等しい疑似配列を「食べる」ことに気付きました。
typeof object.length === 'number' && Number(object.length) >= 0
また、数値が整数である必要はありません(場合を除く)。 JavaScriptは、小数を指定された値以下の最大の整数に変換します。
例:
Array.from({0: ' 1', 1: ' 2', length: 1.6}); // [' 1'] Array.from({0: ' 1', 1: ' 2', 2: ' 3', length: 2.3}); // [' 1', ' 2']
擬似配列を配列に変換する方法は?
擬似配列を配列に変換するには、いくつかのオプションがあります。
- 擬似配列値を通常の配列に列挙します
初心者の頭に浮かぶ最初のオプションは、疑似配列から配列にすべての値をループすることです。
var object = {0: 1, 1: 2, 2: 3, length: 3} var array = []; // for (var i = 0; i < object.length; i++) { array.push(object[i]); }; console.log( array ); // [1, 2, 3]
-
Array.from()
関数を使用する
ブラウザーが異なるサイトでこの機能をサポートするテーブルが異なるため、このオプションは少し議論の余地があります。 しかし、私は自信を持って、すべての最新のブラウザーでこの方法が機能すると言うことができます。
var object = {0: 1, 1: 2, 2: 3, length: 3} // var array = Array.from(object); console.log( array ); // [1, 2, 3]
-
Array.prototype.slice.call()
([].slice.call()
)関数を使用する
これは「私たちの祖父と祖母」の方法であり、現在も機能しています。
var object = {0: 1, 1: 2, 2: 3, length: 3} // var array = Array.prototype.slice.call(object); // : [].slice.call(object); console.log( array ); // [1, 2, 3]
- スプレッド演算子を使用する
この記事を書いている時点でのこの方法は、まだすべてのブラウザでサポートされているわけではなく、「ルート」擬似NodeList
(NodeList
、HTMLCollection
など)でのみ機能するため、かなり議論の余地があります。
var object = document.querySelectorAll(selector); // var array = [...object]; console.log( array ); // [element, element, element]
-
__proto__
プロパティを変更することにより
このプロパティについては、記事の冒頭で説明しました。 オブジェクトのArray.prototype
プロパティをArray.prototype
に変更すると、擬似配列は配列に変換されます。 しかし、このメソッドは、私が書いた「いくつかの場合を除き」に含まれています。なぜなら、配列への完全な変換のためには、length
プロパティは整数でなければならないからです。
var object = {0: 'a', 1: 'b', 2: 'c', length: 3} // __proto__ object.__proto__ = Array.prototype; console.log(object); // ['a', 'b', 'c']
また、ここには1つの機能があります。length
擬似配列のレコード数よりも少ない数に指定すると、length
で指定されたレコード数と残りのレコードから追加のプロパティを持つ配列を取得します。
var object = {0: 'a', 1: 'b', 2: 'c', 3: 'd', 4: 'e', length: 3} // __proto__ object.__proto__ = Array.prototype; console.log(object); // ['a', 'b', 'c', 3: 'd', 4: 'e']
そしてもう1つ注意してください:このメソッドは、オブジェクトを実際の配列にしませんが、必要なパラメーターを与えます。 これを確認するには、Array.isArray();
関数を使用してオブジェクトをチェックしますArray.isArray();
。
var object = {0: 'a', 1: 'b', 2: 'c', 3: 'd', 4: 'e', length: 3} // __proto__ object.__proto__ = Array.prototype; console.log( Array.isArray(object) ); // false
これらは最も一般的な変換方法です。 また、たとえば、
forEach
を使用して擬似
forEach
を反復処理したり、
filter
関数でフィルター処理したりする必要がある場合は、これらすべてのメソッドを省略できることも言う必要があります。 このような目的のために、関数には追加の関数
.call()
があります。これにより、擬似配列を操作できます。
例:
var object = {0: 'a', 1: 'b', 2: 'c', length: 3} // object = Array.prototype.map.call(object, v => ': ' + v); // : [].map.call(object, v => ': ' + v) console.log(object); // [': a', ': b', ': c']
これで、この記事を終了します。 彼は私に彼が何を望んだか、そしてそれがあなたにとって役に立つかどうかはあなた次第だと言った。