4.1 红宝书

2023-01-12 13:27:41 浏览数 (1)

原始值与引用值

原始值:最简单的数据 (Undefined、Null、Boolean、Number、String、Symbol)。我们操作的就是存储在变量的实际值

引用值:多个值构成的对象。是保存在内存中的对象。Js不允许直接访问内存位置,不能直接操作对象所在的内存空间。实际操作的是对该对象的引用。

动态属性

原始值和引用值的定义 都是创建一个变量,然后给它赋值。

  • 引用值可以随时增加、删除、修改其属性和方法。
代码语言:javascript复制
let obj1 = new Object();
obj1.name ="Nike"
console.log(obj1.name)    // Nike

这个给对象obj1新增的属性可以被访问,直到对象销毁或者属性被显式删除。

  • 原始值不能有属性
代码语言:javascript复制
let oldValue = "old"
oldValue.name = "mm"
console.log(oldValue.name)   // undefined

原始值只能使用原始字面量形式,如果使用new关键字,则javaScript创建一个Object类型的实例,但其行为类似原始值

代码语言:javascript复制
let obj = new String("font")
obj.name = "objName"
console.log(obj.name)  // objName
console.log(typeof obj) // object

复制值

首先比较一下复制原始值和引用值的复制

代码语言:javascript复制
//原始值
let value1 = 5;
let value2 = value1;   // 把value1的值复制给了value2
// 我们修改value1 的值  再打印value2
value1 = 8;
console.log(value2);   // 还是 5 
代码语言:javascript复制
// 引用值
let obj1 = new Object();
let obj2 = obj1;      //把obj1 复制给obj2
// 此时改变obj1  再打印obj2
obj1.name = "test"
console.log(obj2)    // {name: 'test'}

区别

  • 原始值的复制是互不干扰的。
  • 引用值复制的实际上是指针,都指向着同一对象。改变一个另一个也会改变

传递参数

ECMAScript中 函数的参数都是按传递的, 也就是函数外的值会被复制到函数内部的参数中。

参数的形式有可能是原始值 也有可能是引用值。

代码语言:javascript复制
 // 原始值
 function Add(num){   // 相当于复制原始值 let num = count
     num  = 10;
     return num;
 }
 let count = 20;  // 变量count
 let result = Add(count)  // 执行函数 传参count
 
 consol.log(count);     // 20 没有变化
 console.log(result);  // 30 
代码语言:javascript复制
// 引用值
function Change(obj){
    obj.name = "test"
    return obj
}
let person = new Object()  // 实例化对象 
let pObj = Change(person)  // 执行函数 参数为person对象

console.log(person)   // {name:'test'}
console.log(pObj)     // {name:'test'}

我们上面说过参数是按值传递的,但是上面这个引用值的例子,在函数内部给obj添加name属性,函数外部对象也会反映这个变化,就感觉引用类型的参数是按引用值传递的。那我们看一下下面的例子

代码语言:javascript复制
function Change(obj){
    obj.name = "test"
    obj = new Object();
    // 变化:新增两行代码 
    obj.name = "wgh"
    return obj
}
let person = new Object()  // 实例化对象 
let pObj = Change(person)  // 执行函数 参数为person对象

console.log(person)   // {name:'test'}
console.log(pObj)     // {name:'wgh'}
  • 如果person是按引用值传递的,那么person应该自动将指针指向name为 wgh 的对象。但是我们再次访问的结果是test,这表明原始的引用值仍然没变。
  • obj在函数内部重写事,变成了一个指向本地对象的指针。这个本地对象在函数执行结束时被销毁。

ECMAScript中函数的参数就是局部变量

确定类型

typeof适用于原始类型,对于引用值只能判断出是object类型。但是我们通常要知道是什么样的对象。 (比如 typeof null回返回object类型)

因此就有了 instanceof操作符

代码语言:javascript复制
 let person = [{'id':1}]
 console.log(person instanceof Object) // true
 console.log(person instanceof Array) // false
 console.log(person instanceof RegExp) // false

instanceof 检查原始值则会始终返回false

0 人点赞