symbol类型
Symbol类型是ECMScript 6 里面 新增的数据类型。符号是原始值,且符号实例是唯一、不可变的的,符号的用途是确保对象属性使用唯一标识符,不会发生属性冲突的危险。
1.符号的基本用法
符号需要Symbol() 函数的初始化。因为符号本身就是原始类型。所有typeof操作符对符号返回 symbol
let sym = Symbol()
console.log(typeof sym) // symbol
symbol不能作为构造函数与new关键字一起使用,这样做是为了避免创建符号包装对象。
let sym = new Symbol() // TypeError: Symbol is bot a constructor
2.使用全局注册表
如果运行时不同部分需要共享和重用符号实例,那么可以用一个字符串作为键,在全局符号注册表中创建并重用符号, 为此需要使用Symbol.for()方法
let sym = Symbol.for('foo');
console.log(typeof sym) // symbol
Symbol.for()对每个字符串键都执行冥等操作。第一次使用某个字符串调用时,它会检查全局运行时注册表,发现不存在对应的符号,于是就会生成一个新符号实例并添加到注册表中.后续使用相同字符串的调用同样会检查注册表,发现存在与该字符串对应的符号。然后就会返回该符号实例。
let sym1 = Symbol.for('foo'); // 创建新符号
let sym2 = Symbol.for('foo'); // 重用已有符号
console.log(sym1 === sym2 ) // true
即是采用相同的符号描述,在全局注册表中定义的符号跟使用Symbol()定义的符号也并不相同;
let sym1 = Symbol('foo');
let sym2 = Symbol.for('foo');
console.log(sym1 === sym2) // false
3.使用符号作为属性
凡是可以使用字符串或数值作为属性的地方,都可以使用符号。对象字面量只能在计算属性语法中使用符号作为属性。
let s1 = Symbol('foo');
let s2 = Symbol('bar')
let s2 = Symbol('bar')
let s2 = Symbol('bar')
let o = {
[s1] : 'foo val' // 可以简写成 0[s1] = 'foo val'
}
console.log(o) // Symbol(foo): "foo val"
Object.defineProperty(o , s2 , {value : 'bar val' })
console.log(o) //Symbol(foo): "foo val" Symbol(bar): "bar val"