1.Javascript實現Symbol

 1 // 當調用 Symbol 的時候,會採用如下步驟:
 2 //1. 若是使用 new ,就報錯
 3 //2. 若是 description 是 undefined,讓 descString 爲 undefined
 4 //3. 不然 讓 descString 爲 ToString(description)
 5 //4. 若是報錯,就返回
 6 //5. 返回一個新的惟一的 Symbol 值,它的內部屬性 [[Description]] 值爲 descString
 7 (function () {
 8     var root = this;
 9     var generateName = (function () {
10         var postfix = 0;
11         return function (descString) {
12             postfix++;
13             return '@@' + descString + '_' + postfix
14         }
15     })()
16     var SymbolPolyfill = function Symbol(description) {
17         // 實現特性第 2 點:Symbol 函數前不能使用 new 命令
18         if (this instanceof SymbolPolyfill) throw new TypeError('Symbol is not a constructor');
19         // 實現特性第 5 點:
20         // 若是 Symbol 的參數是一個對象,toString 方法,將其轉爲字符串,而後才生成一個 Symbol 值。
21         var descString = description === undefined ? undefined : String(descString);
22         var symbol = Object.create({
23             toString: function () {
24                 return this.__Name__;
25             },
26             valueOf: function () {
27                 return this;
28             }
29         })
30         // 語法: Object.defineProperties(obj, props)
31         // obj: 將要被添加屬性或修改屬性的對象
32         // props: 該對象的一個或多個鍵值對定義了將要爲對象添加或修改的屬性的具體配置
33         Object.defineProperties(symbol, {
34             '__Description__': {
35                 value: descString,
36                 writable: false,
37                 enumerable: false,
38                 configurable: false
39             },
40             '__Name__': {
41                 value: generateName(descString),
42                 writable: false,
43                 enumerable: false,
44                 configurable: false
45             }
46         })
47         // 實現特性第 6 點,由於調用該方法,返回的是一個新對象,兩個對象之間,只要引用不一樣,就不會相同
48         //  Symbol 函數的參數只是表示對當前 Symbol 值的描述,相同參數的 Symbol 函數的返回值是不相等的。
49         return symbol
50     }
51     var forMap = {};
52     // Symbol.keyFor 方法返回一個已登記的 Symbol 類型值的 key
53     Object.defineProperties(SymbolPolyfill, {
54         'for': {
55             value: function (description) {
56                 var descString = description === undefined ? undefined : String(description)
57                 return forMap[descString] ? forMap[descString] : forMap[descString] = SymbolPolyfill(descString);
58             },
59             writable: true,
60             enumerable: false,
61             configurable: true
62         },
63         'keyFor': {
64             value: function (symbol) {
65                 for (var key in forMap) {
66                     if (forMap[key] === symbol) return key;
67                 }
68             },
69             writable: true,
70             enumerable: false,
71             configurable: true
72         }
73     })
74     root.SymbolPolyfill = SymbolPolyfill
75 })();
相關文章
相關標籤/搜索