Symbol是[ES6](https://so.csdn.net/so/search?q=ES6&spm=1001.2101.3001.7020)中引入的一种新的基本数据类型,用于表示一个独一无二的值。它是JavaScript中的第七种数据类型,与undefined、null、Number(数值)、String(字符串)、Boolean(布尔值)、Object(对象)并列。
你可以这样创建一个Symbol值:
~~~typescript
const a = Symbol(); console.log(a); //Symbol()
~~~
使用Symbol函数可以生成一个Symbol类型的值,但是你不能在调用Symbol时使用new关键字,因为Symbol是基本数据类型,而不是对象。比如下面的写法是错误的:
~~~typescript
//报错,Symbol is not a constructorconst a = new Symbol();
~~~
使用Symbol()创建一个Symbol类型的值并赋值给a变量后,你就得到了一个在内存中独一无二的值。现在除了通过变量a,任何人在任何作用域内都无法重新创建出这个值。例如当你这样写:
~~~typescript
const b = Symbol();
~~~
尽管a和b都是使用Symbol()创建出来的,但是它们在内存中看起来却是这样的:
![](https://img-blog.csdnimg.cn/20191130113820517.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzQxNjk0Mjkx,size_16,color_FFFFFF,t_70)
实际上,a变量拿到了内存中某块内存的唯一引用(这里所说的引用,其实就是该内存的地址)。如果不借助a变量,你不可能再得到这个地址。因此:
~~~delphi
a !== b; //a和b持有的是两块内存的引用 const c = a; //手动把a里保存的地址保存在c变量中a === c; //c和a现在指向同一块内存,因为它们保存了同样的地址
~~~
![](https://img-blog.csdnimg.cn/20191130134842266.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzQxNjk0Mjkx,size_16,color_FFFFFF,t_70)
这种行为看似难以理解,但其实它与对象遵循相同的规则,如:
~~~delphi
var a = {};var b = {}; a !== b; //a和b各自被分配了不同的内存,因此它们保存了不同的地址 //借助变量a,变量c拿到了a指向的那个对象的地址,因此两者相等var c = a;a === c;
~~~
但是对于同为基本数据类型的[字符串](https://so.csdn.net/so/search?q=%E5%AD%97%E7%AC%A6%E4%B8%B2&spm=1001.2101.3001.7020)来说,它不遵循类似的规则。
比如:
~~~typescript
var a = "123";var b = "123"; a === b; //返回true。两者在常量区引用同一个字符串
~~~
![](https://img-blog.csdnimg.cn/20191130135207337.png?x-oss-process=image/watermark,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3FxXzQxNjk0Mjkx,size_16,color_FFFFFF,t_70)
我们首先通过变量a在内存中创建了字符串“123”,然后在不借助变量a的情况下,又通过var b = "123"拿到了对“123”这个字符串的引用,两者指向内存中的同一块内存地址。
因此我们说,a无法确保别的变量无法拿到它保存的地址(前提是不通过a)。但是对于var a = Symbol()这样的语句,a变量内保存的值是唯一的,因为除了借助a变量,你永远无法得到a中保存的值。这也是Symbol的本质。
可能很多人比较奇怪,一个Symbol类型的变量里面到底保存了什么呢?
我们看两行代码:
~~~typescript
var a = Symbol(); console.log(a); //Symbol()
~~~
我们试图输出a的值,但js引擎输出了Symbol()。显然它不能说明a的值是字符串,因为:
~~~typescript
typeof a === "symbol";
~~~
- vue语法
- vue语法-字符串
- vue事件v-on:
- vue属性绑定v-bind:
- v-if 与v-show使用
- v-for使用
- v-for 遍历json
- v-for 嵌套遍历
- v-html和v-text
- v-cloak
- v-once
- v-pre
- v-on元素添加监听
- v-model
- v-model 数据双向绑定(一般表单用的多)
- v-bind class的应用
- v-bind style使用方法
- 调色板案例 其中用到 v-model和v-bind
- 发布规定限制100字练习
- .stop事件修饰符
- .self事件修饰符
- .prevent事件修饰符
- capture事件修饰符
- once事件修饰符
- 按键修饰符
- 系统修饰符
- 鼠标按键修饰符
- 表单修饰符
- vue-cli脚手架
- cli文件的编译命令与过程
- cli-- mian.js配置文件
- cli-index.html
- cli-app.vue
- cli----组件
- cli----父子传值
- cli--子组件修改父组件值
- 生命周期created
- 计算属性computed
- watch监听
- 计算属性与watch监听实例
- vue组件
- 组件的跟节点注册
- vue全局变量注册方法
- 组件局部注册
- 父子组件通讯
- 组键实战列表
- 动态组件
- keep-alive以及生命周期函数使用
- 单动画过度
- 多元素动画过渡
- 多个组件过渡
- 请求后台api(axios )
- axios请求数据获取json方法
- axios GET请求数据
- axios POST请求数据
- axios GET与POST的另一种写法
- cli 为了防止APP.vue与子组件CSS冲突
- cli静态资源引入(图片等)
- CSS引入
- axios 脚手架里安装以及使用
- vue.config配置跨域问题
- 环境变量
- cli打包上线
- 路由设置router
- router路由跳转方式(编程方式跳转)
- router路由传递参数接受参数
- router嵌套路由
- router动画过渡
- router去掉链接里的#号
- router重定向
- router全局或者局部守卫(登录验证)
- <router-link> 相当于a标签li标签
- <router-view></router-view> 渲染标签
- vuex学习--安装
- vuex-State
- vuex-mutations(函数使用方法)
- 本地存储
- 接口封装
- ES6新语法特性-let const
- ES6-模板字符串 ``反引号
- ES6-对象里函数简化方法
- ES6-箭头函数
- ES6- rest参数
- ES6-Symbol
- ES6-模块化