原始值和引用值
ECMAScript变量可以包含两种不同类型的数据:原始值和引用值,原始值就是最简单的数据:Undefined,Null,Boolean,Number,String,Symbol,保存原始值的变量是按值访问的,因为我们操作的就是存储在变量中的实际值。
引用值是保存在内存中的对象,JavaScript不允许直接访问内存位置,操作对象时,实际上操作的对该对象的引用,而非实际的对象本身,因此,保存引用值的变量是按引用访问的。
区别
动态属性
引用值可以随时添加,修改删除属性。
而原始值不能有属性,原始值的初始化只使用原始字面量形式,如果使用new关键字则JavaScript会创建一个Object类型的实例,
1 | let name1="Nicholas"; |
复制值
通过变量把一个原始值赋值到另一个变量时,原始值会被复制得到新变量的位置。
1 | let num1=5; |
num1和num2相互独立,num2是num1的副本
当把引用值从一个变量赋值给另一个变量时,存储在变量中的值也会被复制到新变量所在位置,区别在于:这里复制的值时一个指针,它指向存储在堆内存中的对象。两个变量实际上指向同一个对象。
1 | let obj1=new Object(); |
传递参数
ECMAScript中所有函数的参数都是按值传递,这意味着函数外的值会被复制到函数内部参数中,就像一个变量赋值到另一个变量一样,如果是原始值,那么就跟原始值变量的复制一样,如果是引用值就和引用值的变量复制一样。
1 | function addTen(num){//count的值被复制到参数num,函数内部num+10但不会影响函数外部的原始变量count |
如果是对象:
1 | function setName(obj){ |
typeof
typeof用来判断一个变量是否为原始类型,即判断一个变量是否为字符串,数字,布尔值或undefined的最好方式,值为对象null,那么typeof返回Object
typeof虽然对原始值很有用,但是对引用值用处不大,我们通常关心一个值是不是对象,而是想知道它是什么类型的对象。
instanceof
如果变量是给定引用类型的实例,则instanceof操作符返回true
1 | console.log(person instanceof Object);//变量person是Object吗 |
按照定义所有引用值都是Object的实例,因此通过instanceof检测的任何引用值和Object构造函数都会返回true。如果,使用instanceof检测原始值,则始终会返回false,因为原始值不是对象。