ES6 new.symbol 的使用方法

阅读时长 6 分钟读完

ES6 新增了一种原始数据类型 Symbol,可以创建一个全局唯一的值。Symbol 作为对象属性的 key,可以保证不会和其他属性名冲突。它的使用方法和意义都值得深入学习和探讨。

1. Symbol 的创建和使用

要创建一个 Symbol,只需要调用全局的 Symbol 函数即可:

由于每个 Symbol 都是全局唯一的,因此每次创建的 Symbol 都不同:

Symbol 也可以接受一个参数,作为 Symbol 的描述,方便调试和识别:

Symbol 作为对象属性的 key,可以保证不会和其他属性名冲突。下面是一个示例:

可以看到,Symbol(mySymbol) 这个属性名不会被其他属性名覆盖,可以用来存储一些特殊的值,避免命名冲突。

2. Symbol 的内置属性

Symbol 还提供了一些内置的属性,用来控制对象的行为。

2.1 Symbol.iterator

Symbol.iterator 用于指定一个对象的遍历器方法。遍历器方法是一个返回遍历器的函数,被 for...of 循环等语句调用。下面是一个示例:

-- -------------------- ---- -------
----- --- - --- -- ---
----- -------- - -----------------------

----------------------------- -- ------- -- ----- ------
----------------------------- -- ------- -- ----- ------
----------------------------- -- ------- -- ----- ------
----------------------------- -- ------- ---------- ----- -----

--- ------ ---- -- ---- -
  ------------------
-
-- -
-- -
-- -

上面的代码中,arrSymbol.iterator 返回一个遍历器对象 iterator,它具有 next 方法,每次调用返回一个遍历元素的对象。通过 for...of 语句也可以遍历数组,相当于调用 arrSymbol.iterator

2.2 Symbol.species

Symbol.species 用于指定对象的构造函数。在创建 object 对象的子类时,可以指定 Symbol.species 为构造函数,这样在创建子类实例时,会使用指定的构造函数。下面是一个示例:

-- -------------------- ---- -------
----- ------- ------- ----- -
  ------ --- ------------------ -
    ------ ------
  -
-

----- --- - --- ---------- -- ---
------------------------- -- --- -- --
----------------------------- -- -----

上面的代码中,MyArray 类继承了 Array 类,并且重写了 slice 方法,返回一个 MyArray 实例。但是,指定了 Symbol.species 为 Array 类,因此使用 slice 方法返回的实例也是 Array 类型。

3. Symbol 的应用场景

Symbol 的应用场景非常广泛,下面列举几个常用的应用场景。

3.1 避免命名冲突

Symbol 可以作为对象属性的 key,避免了命名冲突的问题。下面是一个示例:

-- -------------------- ---- -------
----- ----- - -
  ---- --------------
  ------ ----------------
  ----- --------------
--

-------- ------------- ------ -
  ---------- - -----
-

----- --- - ---
------------- -----------
----------------- -- ------------- -----

------------- -------
----------------- -- ------------- ----- ---- -----

上面的代码中,color 对象使用 Symbol 定义了三种颜色,setColor 函数可以将任何对象的颜色设置为这三种颜色之一。由于颜色是用 Symbol 定义的,因此不会和其他属性名冲突。

3.2 定义常量

Symbol 还可以作为常量的定义。由于每个 Symbol 是全局唯一的,因此可以用 Symbol 定义一个常量:

-- -------------------- ---- -------
----- -------- - ---------- ----- --------

-------- ------- -
  -- ---- --- --------- -
    ---------------- -- -- ----- --------
  - ---- -
    ---------------- -- --- -- ----- --------
  -
-

------------
-------------

上面的代码中,MY_CONST 作为一个常量的定义,传给 fn 函数时,可以比较 arg 是否等于 MY_CONST 来实现一些特殊的逻辑。

3.3 扩展内置对象

Symbol 还可以用来扩展内置对象的方法。下面是一个示例:

-- -------------------- ---- -------
--------------------------------- - ---------- -
  --- - - --
  ------ -
    ----- -- -- --
      ------ -----------------
      ----- - - -----------
    --
  --
--

--- ------ ---- -- -------- -
  ------------------
-
-- ---
-- ---
-- ---
-- ---
-- ---

上面的代码中,使用 Symbol 扩展 String 类型的遍历方法,并使用 for...of 循环遍历字符串的每一个字符。

4. 总结

Symbol 是 ES6 中新增的原始数据类型,创建的每个 Symbol 都是全局唯一的。Symbol 可以作为对象的属性名,避免了命名冲突的问题;还可以作为常量的定义、内置对象的扩展等。Symbol 的内置属性还可以用来控制对象的行为,如遍历方法、构造函数等。掌握 Symbol 的使用方法,可以提高代码的可读性和扩展性。

来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/648d000248841e9894b4b361

纠错
反馈