ES6学习笔记(十)Symbol

本文详细探讨了ES6中的Symbol类型,包括其不可重复的特性、如何通过toString方法转换为字符串、在对象中实现业务逻辑的方法。同时,介绍了Symbol的description属性、多种定义方法及其区别,以及Symbol在区分同名属性、隐藏属性和消除魔法字符串方面的应用场景。
摘要由CSDN通过智能技术生成

Symbol 的语法

Symbol不是一个对象,也没有构造函数,因此无法使用new创建。

可以理解为不可重复的字符串

两个看上去相同的Symbol会返回false

let a = Symbol()
let b = Symbol()
console.log(a === b) // false
let a = Symbol('Faker')
let b = Symbol('Faker')
console.log(a === b) // false

使用toString()方法会返回symbol值的字符串形式

let a = Symbol('Faker')
console.log(a.toString()) // Symbol(Faker)

对于对象,可以通过改写toString来实现一些业务逻辑

let obj = {
    name: 'Faker',
    toString() {
        return this.name
    }
}
let a = Symbol(obj)
console.log(a.toString()) // Symbol(Faker)

description

一个API,用于返回描述。一个字符串

let a = Symbol('Faker')
console.log(a.description) // Faker

不同的定义方法

使用普通的定义方法时,会将Symbol独立生成

let a = Symbol('Faker')
let b = Symbol('Faker')
console.log(a === b) // false

使用for定义时,会在全局环境中注册,如果内容相同,则多个Symbol会指向相同的数据地址。

let a = Symbol.for('Faker')
let b = Symbol.for('Faker')
console.log(a === b) // true

可以使用静态方法keyFor()查询注册在全局变量中的Symbol

let a = Symbol.for('Faker')
console.log(Symbol.keyFor(a)) // Faker

Symbol的用途

区分同名属性

独一无二:将Symbol作为属性的key,保证同名属性之间并不冲突。

如果一个类中有两个同名属性,使用一般方法则不能保证互相区分开。

如下,两个都叫Faker的队员只会输出一个Faker

let SKT = {
    Faker: { name: 'Faker', age: 24, play: 'Mid' },
    Faker: { name: 'Faker', age: 24, play: 'Bot' }
}
console.log(SKT) // {Faker: {…}}

如果使用Symbol作为属性的Key,则可以很好地将同名属性分开。

let mid = Symbol('Faker')
let bot = Symbol('Faker')
let SKT = {
    [mid]: { name: 'Faker', age: 24, play: 'Mid' },
    [bot]: { name: 'Faker', age: 24, play: 'Bot' }
}
console.log(SKT) // {Symbol(Faker): {…}, Symbol(Faker): {…}}
console.log(SKT[mid]) // {name: "Faker", age: 24, play: "Mid"}
console.log(SKT[bot]) // {name: "Faker", age: 24, play: "Bot"}

隐藏属性

类似于私有属性,封装

一般的对象遍历方式无法遍历以Symbol作为Key的属性。

这里列出了不同遍历方式对于遍历到属性形式的影响。

let mid = Symbol('Faker')
let SKT = {
    [mid]: { name: 'Faker', age: 24, play: 'Mid' },
    Bang: { name: 'Bang', age: 24, play: 'Bot' }
}

// 普通遍历 只能遍历普通属性
for (let a in SKT) {
    console.log(a, SKT[a]) // Bang {name: "Bang", age: 24, play: "Bot"}
}

// Object.keys() 只能遍历普通属性
for (let key of Object.keys(SKT)) {
    console.log(key, SKT[key])
    // Bang {name: "Bang", age: 24, play: "Bot"}
}

// Object.getOwnPropertyNames() 指定遍历普通属性
for (let key of Object.getOwnPropertyNames(SKT)) {
    console.log(key, SKT[key])
    // Bang {name: "Bang", age: 24, play: "Bot"}
}

// Object.getOwnPropertySymbols() 指定遍历Symbol作为Key的属性
for (let key of Object.getOwnPropertySymbols(SKT)) {
    console.log(key, SKT[key])
    // Symbol(Faker) {name: "Faker", age: 24, play: "Mid"}
}

// 所有属性形式均可遍历
for (let key of Reflect.ownKeys(SKT)) {
    console.log(key, SKT[key])
    // Bang {name: "Bang", age: 24, play: "Bot"}
    // Symbol(Faker) {name: "Faker", age: 24, play: "Mid"}
}

消除魔法字符串

魔法字符串:指的是,在代码之中多次出现、与代码形成强耦合的某一个具体的字符串或数值。风格良好的代码,应该尽量消除魔法字符串,而由含义清晰的变量代替。

由于Symbol独一无二的特性,可以很好地代替魔法字符串。

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值