Symbol について
■ Symbol について
ECMAScript 6 世代の機能です。
■ Symbol オブジェクトについて
Symbol オブジェクトは、リファレンス型に該当します。
typeof 演算子を使用すると、"symbol" という文字列が得られます。
■ Symbol オブジェクトの種類について
「ローカルなシンボル」と「グローバルなシンボル」の2種類があります。
■シンボルプロパティとして活用する
任意のオブジェクトに、シンボルプロパティを追加する事ができます。
ローカルなシンボルについて
■ローカルな Symbol オブジェクトを作成する
Symbol() 関数を使用します。
Symbol( "description" ) :Symbol
第01引数(略可) | String | 好きな説明文を指定(デバッグ用) |
戻り値 | Symbol | 新しい Symbol オブジェクトが得られる。 |
■第01引数(説明文)
通常は、指定する必要はありません。
第01引数の指定は、新しい Symbol オブジェクトに影響しません。
開発者が、デバッガなどから、Symbol の利用目的を確認する為に利用します。
■戻り値(Symbol)
必ずユニーク(唯一)な、Symbol オブジェクトが生成されます。
■使用例
Symbol オブジェクトを作成する
// ------------------------------------------------------------
// Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_obj0 = Symbol();
var symbol_obj1 = Symbol();
// 出力テスト
console.log(symbol_obj0);
console.log(symbol_obj1);
// ------------------------------------------------------------
// Symbol オブジェクトを作成する(デバッグ用の説明文付き)
// ------------------------------------------------------------
var symbol_obj2 = Symbol( "説明文A" );
var symbol_obj3 = Symbol( "説明文B" );
// 出力テスト
console.log(symbol_obj2);
console.log(symbol_obj3);
グローバルなシンボルについて
■グローバルな Symbol オブジェクトを作成する
Symbol.for() メソッドを使用します。
Symbol.for( "key" ) :Symbol
第01引数 | String | キー情報(識別名)を指定 |
戻り値 | Symbol | グローバルな Symbol オブジェクトが得られる。 |
■第01引数(キー情報)
キー情報(識別名)を指定します。
ユニーク(唯一)な識別名を指定した場合、必ず新しい Symbol オブジェクトが得られます。
以前と同じ識別名を指定した場合、最初に作成した Symbol オブジェクトが得られます。
■使用例
グローバルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
// グローバルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_a0 = Symbol.for( "key_a" );
var symbol_b0 = Symbol.for( "key_b" );
var symbol_c0 = Symbol.for( "key_c" );
// 出力テスト
console.log(symbol_a0);
console.log(symbol_b0);
console.log(symbol_c0);
// ------------------------------------------------------------
// 以前と同じ Symbol オブジェクトを取得する
// ------------------------------------------------------------
var symbol_a1 = Symbol.for( "key_a" );
var symbol_b1 = Symbol.for( "key_b" );
var symbol_c1 = Symbol.for( "key_c" );
// 出力テスト
console.log(symbol_a0 == symbol_a1); // true
console.log(symbol_b0 == symbol_b1); // true
console.log(symbol_c0 == symbol_c1); // true
console.log(symbol_a0 == symbol_b0); // false
console.log(symbol_a0 == symbol_c0); // false
console.log(symbol_b0 == symbol_c0); // false
■グローバルな Symbol オブジェクトから、キー情報(識別名)を取得する
Symbol.keyFor() メソッドを使用します。
ローカルな Symbol オブジェクトを指定すると失敗します。
この場合、undefined 値が得られます。
Symbol.keyFor( symbol ) :String
第01引数 | Symbol | グローバルな Symbol オブジェクトを指定 |
戻り値 | String | キー情報(識別名)が得られる。失敗した場合 undefined 値が得られる |
■使用例
グローバルな Symbol オブジェクトから、キー情報(識別名)を取得する
// ------------------------------------------------------------
// グローバルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_a = Symbol.for( "key_a" );
var symbol_b = Symbol.for( "key_b" );
var symbol_c = Symbol.for( "key_c" );
// ------------------------------------------------------------
// グローバルな Symbol オブジェクトから、キー情報(識別名)を取得する
// ------------------------------------------------------------
var name_a = Symbol.keyFor( symbol_a );
var name_b = Symbol.keyFor( symbol_b );
var name_c = Symbol.keyFor( symbol_c );
// 出力テスト
console.log(name_a); // "key_a"
console.log(name_b); // "key_b"
console.log(name_c); // "key_c"
// ------------------------------------------------------------
// ローカルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_d = Symbol( "説明文D" );
// ------------------------------------------------------------
// キー情報(識別名)の取得を試みる(ローカルな Symbol オブジェクトなので失敗する)
// ------------------------------------------------------------
var name_d = Symbol.keyFor( symbol_d );
// 出力テスト
console.log( name_d ); // undefined
シンボルプロパティについて
■シンボルプロパティとは?
Symbol オブジェクトは、任意のオブジェクトのキーとして利用できます。
こうして追加されるプロパティは、シンボルプロパティと呼ばれます。
■従来の API との互換性について
シンボルプロパティは、従来の方法で検出する事はできません。
これにより、旧世代のライブラリ資産は、そのまま安全に利用できます。
イテレーターなどの次世代の仕様と干渉する事はありません。
■シンボルプロパティにアクセスする
■シンボルプロパティにアクセスする
配列アクセス演算子を使用します。
ドットアクセス演算子は利用できません。
任意のオブジェクトにシンボルプロパティを追加する
// ------------------------------------------------------------
// Object オブジェクトを作成する
// ------------------------------------------------------------
var obj = new Object();
// ------------------------------------------------------------
// Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_a = Symbol();
var symbol_b = Symbol();
var symbol_c = Symbol();
// ------------------------------------------------------------
// シンボルプロパティを追加して、値をセットする
// ------------------------------------------------------------
obj[symbol_a] = 123;
obj[symbol_b] = "あいう";
obj[symbol_c] = {a:0,b:1,c:2};
// ------------------------------------------------------------
// シンボルプロパティから値を取得する
// ------------------------------------------------------------
var value_a = obj[symbol_a];
var value_b = obj[symbol_b];
var value_c = obj[symbol_c];
// ------------------------------------------------------------
// 出力テスト
// ------------------------------------------------------------
console.log( value_a ); // 123
console.log( value_b ); // "あいう"
console.log( value_c ); // {a:0,b:1,c:2}
■シンボルプロパティを削除する
シンボルプロパティを削除するには、delete 文を使用します。
任意のオブジェクトから、シンボルプロパティを削除する
// ------------------------------------------------------------
// Object オブジェクトを作成する
// ------------------------------------------------------------
var obj = new Object();
// ------------------------------------------------------------
// Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_a = Symbol();
var symbol_b = Symbol();
var symbol_c = Symbol();
// ------------------------------------------------------------
// シンボルプロパティを追加して、値をセットする
// ------------------------------------------------------------
obj[symbol_a] = 123;
obj[symbol_b] = "あいう";
obj[symbol_c] = {a:0,b:1,c:2};
// ------------------------------------------------------------
// シンボルプロパティを削除する
// ------------------------------------------------------------
delete obj[symbol_a];
delete obj[symbol_b];
delete obj[symbol_c];
■オブジェクトからシンボルプロパティをまとめて取得する
Object.getOwnPropertySymbols ( オブジェクト ) :Array
第01引数 | Object | オブジェクトを指定。 |
戻り値 | Array | Symbol オブジェクトが格納された配列が得られる。 |
■使用例
シンボルプロパティのキーとなる Symbol オブジェクトをまとめて取得する
// ------------------------------------------------------------
// Object オブジェクトを作成する
// ------------------------------------------------------------
var obj = new Object();
// ------------------------------------------------------------
// ローカルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_a = Symbol( "説明文A" );
var symbol_b = Symbol( "説明文B" );
var symbol_c = Symbol( "説明文C" );
// ------------------------------------------------------------
// グローバルな Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol_d = Symbol.for( "key_d" );
var symbol_e = Symbol.for( "key_e" );
var symbol_f = Symbol.for( "key_f" );
// ------------------------------------------------------------
// シンボルプロパティを追加して、値をセットする
// ------------------------------------------------------------
obj[symbol_a] = "value_a";
obj[symbol_b] = "value_b";
obj[symbol_c] = "value_c";
obj[symbol_d] = "value_d";
obj[symbol_e] = "value_e";
obj[symbol_f] = "value_f";
// ------------------------------------------------------------
// シンボルプロパティのキーをまとめて取得する(Symbol オブジェクトのリスト)
// ------------------------------------------------------------
var symbol_list = Object.getOwnPropertySymbols ( obj );
// 出力テスト
console.log(symbol_list); // { length:6 , ...
■シンボルプロパティの参照強度について
シンボルプロパティは、強参照です。
Object.getOwnPropertySymbols() メソッドを利用すると、いつでもキーとなる Symbol オブジェクトにアクセスできます。
シンボルプロパティを明示的に削除しなかった場合、キーとなる Symbol オブジェクトと、格納した値は、生存し続けます。
オブジェクト自体がガベージコレクションの対象となった場合、シンボルプロパティも連動して消滅します。
シンボルプロパティの参照強度を確認する
// ------------------------------------------------------------
// Object オブジェクトを作成する
// ------------------------------------------------------------
var obj = new Object();
// ------------------------------------------------------------
// Symbol オブジェクトを作成する
// ------------------------------------------------------------
var symbol = Symbol();
// ------------------------------------------------------------
// 128 MByte 相当のデータを用意する
// ------------------------------------------------------------
var ary_u8 = new Uint8Array(1024 * 1024 * 128);
// ------------------------------------------------------------
// シンボルプロパティを追加して、値をセットする
// ------------------------------------------------------------
obj[symbol] = ary_u8;
// ------------------------------------------------------------
// 変数に null をセット(シンボルプロパティは消滅しない)
// ------------------------------------------------------------
symbol = null;
ary_u8 = null;
// ------------------------------------------------------------
// Object オブジェクトから Symbol オブジェクトを取得できる
// ------------------------------------------------------------
// シンボルプロパティのキーをまとめて取得する(Symbol オブジェクトのリスト)
var symbol_list = Object.getOwnPropertySymbols ( obj );
// Symbol オブジェクトを取得する
symbol = symbol_list[0];
// ------------------------------------------------------------
// 変数に null をセット(オブジェクト自体が消滅する場合、シンボルプロパティも消滅する)
// ------------------------------------------------------------
obj = null;