在 JavaScript 中,每个变量都可以用字符串作为标识符来引用。但是一些特殊情况下,字符串标识符是不够用的。为了解决这个问题,ECMAScript 引入了 Symbol,它是一种基本数据类型,可以用于创建独一无二的标识符。
什么是 Symbol
Symbol 是 ECMAScript 引入的第七种基本数据类型,它的特点是值是唯一的,且不能被修改。使用 Symbol,可以创建一些唯一的标识符,以避免命名冲突。
let id1 = Symbol(); let id2 = Symbol(); console.log(id1 === id2); // false
Symbol Description
除了创建 Symbol 实例之外,还可以为它们添加一个可选的 Symbol Description 字符串参数。Symbol Description 字符串参数不会影响 Symbol 的唯一性。
let id1 = Symbol('id'); let id2 = Symbol('id'); console.log(id1 === id2); // false
如何使用 Symbol
为对象添加 Symbol 属性
可以通过 Symbol 创建唯一的对象属性。通常情况下,对象属性的名称都是字符串,这样容易导致命名冲突。使用 Symbol 创建对象属性时,可以避免这种情况的发生。
let user = { [Symbol('name')]: 'Tom', [Symbol('age')]: 18, }; console.log(user); // {Symbol(name): "Tom", Symbol(age): 18}
内置的 Symbol
ECMAScript 中还定义了一些内置的 Symbol,它们具有特定的含义,可以用来扩展对象的行为。
Symbol.iterator
Symbol.iterator 是一个用于指定对象迭代器的属性。在对象上使用 for..of 遍历时,会调用 Symbol.iterator 属性对应的方法。
let arr = [1, 2, 3]; let iterator = arr[Symbol.iterator](); console.log(iterator.next()); // {done: false, value: 1} console.log(iterator.next()); // {done: false, value: 2} console.log(iterator.next()); // {done: false, value: 3} console.log(iterator.next()); // {done: true, value: undefined}
Symbol.toStringTag
Symbol.toStringTag 是一个用于定制对象的 toString 方法在输出时的标签。此方法可以接收一个自定义名称的 Symbol,并输出一个定制的字符串标签。
let user = { [Symbol.toStringTag]: 'User', name: 'Tom', age: 18, }; console.log(user.toString()); // "[object User]"
Symbol.hasInstance
Symbol.hasInstance 是一个用于定制对象在 instanceof 操作中的行为的方法。此方法可以接收一个函数,并在 instanceof 操作时调用该函数。
下面的代码是通过一个 Person 类来定义一个对象,再通过 instanceof 操作符对其进行检测。在 Symbol.hasInstance 方法中添加一个函数,可以实现自定义的检测规则。
class Person { static [Symbol.hasInstance](obj) { return obj instanceof Array; } } console.log([] instanceof Person); // true console.log({} instanceof Person); // false
总结
Symbol 是一种基本数据类型,通过它可以创建唯一的标识符。除了可以为对象添加唯一的属性之外,还可以使用内置的 Symbol,从而扩展对象的行为。在实际应用中,使用 Symbol 可以有效避免命名冲突,提高代码的可维护性。
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/6499018848841e98945f30aa