数据类型Symbol
一、什么是Symbol
Symbol实际上是ES6引入的一种原始数据类型,用来产生一个独一无二的值
二、Symbol的使用
let sym=Symbol('aa');
console.log(sym);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UGiwHFcL-1635344964290)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930153947735.png)]
三、Symbol函数前不能用new
Symbol函数不是一个构造函数,前面不能用new操作符,所以Symbol类型的值也不是一个对象,不能添加任何属性,它只是一个类似于字符型的数据类型,如果强行在Symbol函数前加上new操作符,会报错
let sym=new Symbol();
console.log(sym);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ICaJdGiX-1635344964293)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930154301629.png)]
使用注意事项
1、Symbol前面不能加new,加new就报错
2、Symbol返回的是一个唯一值,通常使用最唯一的key使用
3、Symbol是一种单独的数据类型,就叫Symbol,是基本数据类型
4、如果Symbol为了key,那么for…in…循环,是循环不出来Symbol的key的
四、Symbol的用处
作为key使用
let symbol=Symbol('a');
let obj={
a:'aa',
b:'bb',
[symbol]: '我是symbol'
}
console.log(obj.a);
console.log(obj[symbol]);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-S0VHJGwB-1635344964295)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930155342510.png)]
4.1、字符串作为参数
Symbol函数还可以接受一个字符串参数,对产生的Symbol值进行描述,方便我们区分不同的Symbol值,给Symbol函数加了参数之后,控制台输出的时候可以区分到底是哪一个值,Symbol函数只是对当前Symbol值的描述,因此相同参数的Symbol函数返回值是不相等的
let s1=Symbol('s1');
let s2=Symbol('s2');
let s3=Symbol('s2');
console.log('s1',s1);
console.log('s2',s2);
console.log('s3',s3);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LO7MBkwr-1635344964297)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930163302020.png)]
4.2、对象转为参数
如果Symbol函数的参数是一个对象,就会调用该对象的toString方法,将其转化为一个字符串,然后才生成了一个Symbol值,所以,Symbol函数的参数只能是字符串
let sym=Symbol({});
console.log(sym);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SqUBUWiH-1635344964298)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930163956223.png)]
4.3、Symbol值不可以进行运算
Symbol值是不能进行运算的,不仅不能喝Symbol值进行运算,也不能喝其他类型的值进行运算,否则会报错
Symbol值可以显示转化为字符串和布尔值,但是不能转为数值
let sym1=Symbol('1');
let sym2=Symbol('3');
console.log(sym1+sym2);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-PlrGNZgF-1635344964299)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930164430320.png)]
4.4Symbol作为属性
Symbol就是为对象的属性名而生的
//第一种写法
let obj={};
let sym=Symbol();
obj[sym]='symbol';
console.log(obj);
//第二种写法
let obj={};
let sym=Symbol();
obj={
[sym]:'symbol'
}
console.log(obj);
//第三种写法
let obj={};
let sym=Symbol();
Object.defineProperty(obj,sym,{
value:'symbol'
})
console.log(obj);
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-IoiPDMTQ-1635344964299)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930172502817.png)]
使用对象的Symbol值作为属性名时,获取相应的属性值不能用点运算符,
如果用点运算符来给对象的属性赋Symbol类型的值,实际上属性名会变成一个字符串,而不是一个Symbol值
在对象内部,使用Symbol值定义属性时,Symbol值必须放在方括号之中,否则只是一个字符串。
4.5、Symbol值作为属性名的遍历
使用for...in...
和for...of...
无法遍历到Symbol值的属性,Symbol值作为对象的属性名,也无法通过Object.keys()
、object.getOwnPropertyName()
来获取,只能通过Object.getOwnPropertySymbol()
来获取一个对象上的Symbol
属性名
let sym1=Symbol('sym1');
let sym2=Symbol('sym2');
let obj={
name:'zhangsan',
[sym1]:'sym1',
[sym2]:'sym2'
}
console.log(obj);
console.log(Object.getOwnPropertySymbols(obj));
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-rTaPDw8E-1635344964300)(C:\Users\web\AppData\Roaming\Typora\typora-user-images\image-20210930175347861.png)]