14、ES6的Symbol

一、Symbol是什么。

Symbol是ES6引入的一种原始数据类型,除了Symbol,JavaScript还有其他5种数据类型,分别是 

  • Undefined
  • Boolean
  • String
  • Number
  • 对象

这5种数据类型都是ES5中就有的。

二、Symbol作用。

1、Symbol的值是唯一的。

 每次创建的Symbol 都是唯一不重复的,也就是类似UUID的东西。每次创建的值都是唯一的。如下:

    let symb1 = Symbol();
    let symb2 = Symbol();
    console.log(symb1,symb2);//打印  Symbol() Symbol()
    console.log(symb1==symb2);//打印  false

虽然symb1,symb2打印出字符串表示都是Symbol()一样的,但是symb1和symb2的值不相等。

2、作用。

我们在创建对象的时候,有时候需要定义的属性名是唯一的,避免冲突。

 比如在表格中,需要点击表格头部实现排序。我们给表头添加一个属性sort=asc。但是并不能保证其他第三方组件不会在表头也添加一个sort属性。这时候第三方组件有可能操作我们的sort属性导致冲突。

这时候我们可以按照下面这样做。

 let sort = Symbol("my sort");
    let tablehead = {
        username: "lisi",
        [sort]: "ASC" //给tablehead增加一个属性
    }
    console.log(tablehead[sort]);//打印ASC

我们给tablehead对象增加了一个属性,这个属性的名字是Symbol("my sort")方法的返回值。所以返回值sort是唯一的。这样就可以和其他组件互相不冲突。

三、Symbol的创建。

1、普通创建。

直接调用Symbol()函数创建,或者传递一个字符串参数创建。

let symb1 = Symbol();
//传入字符串创建Symbol
symb1 = Symbol("my symbol");

2、Symbol.for()。

Symbol.for(key)先在全局环境中查找是否有key对应的Symbol值。如果有就返回这个值。没有就会生成新的 Symbol,并且把这个新的Symbol放在全局环境中。

let s1 = Symbol.for('foo');
let s2 = Symbol.for('foo');

s1 === s2 // true

上面代码中,s1和s2都是 Symbol 值,但是它们都是同样参数的Symbol.for(key)方法生成的,所以实际上是同一个值。

Symbol.for(key)与Symbol()这两种写法,都会生成新的 Symbol。它们的区别是,前者会被登记在全局环境中供搜索,后者不会。Symbol.for(key)不会每次调用就返回一个新的 Symbol 类型的值,而是会先检查给的key是否已经存在,如果不存在才会新建一个值。

Symbol.for("bar") === Symbol.for("bar")
// true

Symbol("bar") === Symbol("bar")
// false

上面代码中,因为Symbol()写法没有登记机制,所以每次调用都会返回一个不同的值。

 

四、Symbol.keyFor()。

Symbol.keyFor(),接收Symbol 做参数。方法返回一个已登记的 Symbol 类型值的key。

let s1 = Symbol.for("foo");
Symbol.keyFor(s1) // "foo"

let s2 = Symbol("foo");
Symbol.keyFor(s2) // undefined

上面代码中,变量s2属于未登记的 Symbol 值,所以返回undefined。

五、Symbol作为属性名。

Symbol 值作为属性名,给对象添加Symbol类型的属性名时,不能使用点运算符。只能用中括号[]。

   let symb1 = Symbol("my symbol");

    let obj = {username:"lisi"};
    // obj.symbol = "dsfsd";//这种写法是错误的。
    obj[symb1] = "1233";
    console.log(obj[symb1]);//1233

直接在创建对象的时候写,如下:

let symb1 = Symbol("my symbol");
let obj = {
    username:"lisi",
    [symb1]: "1233"
}
console.log(obj[symb1]);// 1233

作为方法名,如下:

let symb1 = Symbol("my symbol");
let obj = {
    username:"lisi",
    [symb1]: function () {
        //ssss
    }
}
console.log(obj[symb1]);

也是作为方法名。但是简写了方法。如下:

let symb1 = Symbol("my symbol");
let obj = {
    username:"lisi",
    [symb1]() {
        //ssss
    }
}
console.log(obj[symb1]);

六、Symbol作为属性名的遍历。

Symbol 作为属性名,该属性不会出现在for...in、for...of循环中,也不会被Object.keys()、Object.getOwnPropertyNames()、JSON.stringify()返回。但是,它也不是私有属性,有一个Object.getOwnPropertySymbols方法,可以获取指定对象的所有 Symbol 属性名。

例子如下:

let symb1 = Symbol("my symbol");
    let symb2 = Symbol("my symbol 2");
    let obj = {
        username:"lisi",
        [symb1]() {
            //ssss
        },
        [symb2]:"123"
    }
    for (let i in obj){
        console.log(i);//只能输出 username ,并不能输出Symbol值的属性名
    }
    //不能取得Symbol值的属性名
    console.log(Object.getOwnPropertyNames(obj));//["username"]
    //Object.getOwnPropertySymbols(obj) 获得对象的所有Symbol值的属性名
    console.log(Object.getOwnPropertySymbols(obj));//[Symbol(my symbol), Symbol(my symbol 2)]

    //["username", Symbol(my symbol), Symbol(my symbol 2)] 所有属性名
    console.log(Reflect.ownKeys(obj));

对上面的代码。有奇点总结:

  • Object.getOwnPropertyNames(obj) 只能返回非Symbol的属性名。
  • for...in只能遍历非Symbol的属性名。
  • Object.getOwnPropertySymbols(obj) 返回对象的所有Symbol的属性名。
  • (Reflect.ownKeys(obj) 返回对象的所有属性名。
     

其他内容,请参考http://es6.ruanyifeng.com/#docs/symbol 。

 

转载于:https://my.oschina.net/kunBlog/blog/1635729

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值