JavaScriptでは文字列や数字の他に、配列やオブジェクトと言った型があります。おそらく利用した経験がある方も多いでしょう。この配列とオブジェクトに対して、より便利な機能を提供するのがSetオブジェクトとMapオブジェクトです。
この記事では配列やオブジェクトとの違いを、コードで解説していきます。
Setオブジェクト
Setオブジェクトは配列(Array)に相当するものだと言えます。
const set = new Set;
const ary = [];
一番大きな違いとして、Setは同じ値が追加できないという点が挙げられます。
set.add('a');
// => Set(1) {'a'}
set.add('a');
// => Set(1) {'a'}
もちろん配列の場合は、同じ値も追加できます。
ary.push('a');
ary.push('a');
// => ['a', 'a']
このユニークな値しか追加できないという点がメリットになる場合もあるでしょう。
Setオブジェクトのメソッドは基本的に配列と同じように操作できるものが揃っています。
要素を追加する
要素を追加するのは add
メソッドです。
set.add('a');
set.add('b');
要素を削除する
delete
メソッドで値を指定して削除できます。
set.delete('a');
すべて削除して空にする場合には clear
メソッドを使います。
set.clear();
値が存在するか確認する
has
メソッドを使って値の存在を確認します。
if (set.has('a')) {
// 値あり
} else {
// 値なし
}
イテレーションを使ったループ処理
Setオブジェクトでは for of
を使った各種イテレーションが利用できます。たとえば、以下のようなオブジェクトを定義します。
const set = new Set;
set.add('テキスト');
set.add(100);
set.add(true);
この時、setだけでイテレーションができます。keys
や values
といったメソッドもありますが、同じデータが返ってきます。
for (let item of set) console.log(item)
// => テキスト
// => 100
// => true
forEach
メソッドも利用できます。
set.forEach(item => console.log(item));
// => テキスト
// => 100
// => true
配列への変換
Setオブジェクトから配列にする際には Array.from
を利用します。
Array.from(set);
// => ['テキスト', 100, true]
Mapオブジェクト
Mapオブジェクトはオブジェクト型に相当するものになります。
const map = new Map;
const obj = {};
初期化する際に2次元配列を渡すことで、データを含めたMapオブジェクトを作成できます。入れ子になっている配列の1つめの値がキー、2つめが値になります。
const map = new Map([
[1, 'one'],
[2, 'two'],
[3, 'three'],
]);
Mapの特徴としては、キーの型が自由である点が挙げられます。オブジェクト型は文字列またはシンボルしかキーに使えませんが、Mapは関数やオブジェクトなどもキーにできます。
const map = new Map;
const date = new Date;
map.set(date, 10);
map.get(date);
// => 10
function func() {}
map.set(func, 30);
map.get(func);
// => 30
データの追加と取得
データの追加は set
、取得は get
メソッドを使います。キーを使って追加もできますが、正しく動作しなくなるので注意してください。
const map = new Map;
const date = new Date;
map.set(date, 10);
map.get(date);
// => 10
データの削除
データの削除は delete
メソッドを使って行います。
map.delete(date);
データをすべて削除する場合は clear
メソッドを使います。
map.clear();
データの数を取得
Mapオブジェクトには size
プロパティが用意されており、簡単にデータの個数を取得できます。オブジェクトの場合は Object.keys
を使っていたでしょう。
map.size;
// => 3
キーの存在を確認
指定したキーが存在するかどうかは has
メソッドで確認できます。
if (map.has(date)) {
// キーが存在する
} else {
// キーが存在しない
}
イテレーションを使ったループ処理
Mapオブジェクトでは for of
を使った各種イテレーションが利用できます。たとえば、以下のようなオブジェクトを定義します。
const map = new Map;
map.set('テキスト', 100);
map.set(10, 200);
map.set(true, 300);
この時、mapだけでイテレーションできます。キーと値が配列で取得できます。これは entries
メソッドと同じです。
for (let [key, item] of map) console.log({key, item})
// => {key: 'テキスト', item: 100}
// => {key: 10, item: 200}
// => {key: true, item: 300}
キーを取得してイテレーションを行う場合には keys
メソッドを使います。
for (let item of map.keys()) console.log(item)
// => 'テキスト'
// => 10
// => true
逆に値を使う場合には values
メソッドを使います。
for (let item of map.values()) console.log(item)
// => 100
// => 200
// => 300
forEach
メソッドも利用できます。
map.forEach((item, key) => console.log({key, item}));
// => {key: 'テキスト', item: 100}
// => {key: 10, item: 200}
// => {key: true, item: 300}
まとめ
SetオブジェクトやMapオブジェクトは配列やオブジェクトで代替が効くケースも多いので、あまり利用されていないかも知れません。しかしfor文よりもforEachなどが使われることが増えている現在、使い方を覚えておくと便利に使える場面も多いでしょう。
ぜひ使いこなしてください。