在JavaScript中读取/分配引用类型

在JavaScript中读取/分配引用类型,javascript,ecmascript-6,computer-science,Javascript,Ecmascript 6,Computer Science,我喜欢认为我已经理解了引用类型,但我想知道我在这里遗漏了什么,在引擎盖下发生了什么 let o = { foo: 'bar' }; console.log(o) // logs the object. let p = o; // assigns reference to object 我已经看了一千遍了,然后不假思索地继续前进,但这一次它给了我意想不到的幻觉震撼 在这两种情况下,我的大脑都把这理解为“读取o和的值”。但是,其中一个将记录存储的实际数据,而另一个将返回引用。我遗漏了哪一

我喜欢认为我已经理解了引用类型,但我想知道我在这里遗漏了什么,在引擎盖下发生了什么

let o = {
   foo: 'bar'
};

console.log(o) // logs the object.

let p = o; // assigns reference to object
我已经看了一千遍了,然后不假思索地继续前进,但这一次它给了我意想不到的幻觉震撼

在这两种情况下,我的大脑都把这理解为“读取o和的值”。但是,其中一个将记录存储的实际数据,而另一个将返回引用。我遗漏了哪一步使这两行不同

设p=o;事情通常是如何运作的,但是 console.logo导致某种类型的隐式/默认调用

还是相反,o会自然地拉动实际物体 从堆中分配,但分配本质上总是分配 推荐人

什么时候x会变成z

有人能解释一下它的工作原理,让我明白它的确切原因吗?

如果复制值,那么就复制对对象的引用

如果您对它做了任何其他操作,那么将遵循引用并使用对象

o的值是对对象的引用

如果将o指定给p,则复制该引用,p也是对对象的引用

如果您访问o.foo,那么您将遵循对该对象的引用,并对其foo属性进行处理


如果将o传递给函数,则将引用复制到函数中的参数。如果该函数随后访问paramater.foo,那么它将遵循对该对象的引用,并使用其上的foo值执行某些操作。

在您的代码示例中,o和p都是指向同一底层Javascript对象的指针

执行此操作时:

let o = {
   foo: 'bar'
};
o包含指向Javascript对象的指针。重要的是不要认为o包含对象本身。它包含一个指向对象的指针,对象独立于任何一个变量本身而存在。我故意不把它称为对对象的引用,因为它的行为与引用不完全一样。如果我给p赋值,它不会以任何方式改变o,因此它不是一个完整的引用。它的行为就像C语言中的指针一样

在中指定这样的指针时:

let p = o;
Javascript从o复制指针并将其放入p变量中。现在,每个变量o和p都包含指向同一对象的指针。如果通过o或p指针修改对象,则每个指针只指向一个对象,因此无论使用哪个变量查看基础对象,都可以看到修改

// create an object and assign a pointer to that object to the variable o
let o = {
   foo: 'bar'
};

// assign a pointer to the same object to the variable p
let p = o;

// modify the object pointed to by o
o.foo = 'hello';

// since both variables point to the same object, both see the modification
console.log(o.foo);    // 'hello'
console.log(p.foo);    // 'hello'
o和p都指向同一个底层对象。因此,修改该对象,无论您使用哪个指针来修改它,都将修改基础对象,并且两个指针仍将指向现在修改的相同对象

p不是o的引用,因为如果我给p赋值,它根本不会影响o

将该指针传递到函数时,如中所示:

console.log(o);
它再次使指针的副本不是对象的副本,并将其作为参数传递给函数。然后由调用的函数决定如何处理传递给它的参数。在本例中,console.log查看参数的类型,发现它是指向对象的指针,然后决定使用它拥有的代码输出对象的内容。console.log的内部工作分析参数的类型并决定如何处理它


将对象传递给Javascript中的函数就像将该对象分配给另一个变量,事实上,Javascript就是这么做的。它创建一个新的临时变量,作用域为该函数,并将指针的副本分配给该对象,然后使该命名参数变量在该函数的作用域内可用。然后,函数可以通过指向该对象的本地指针访问该对象。

是什么让您认为这两个示例有所不同?赋值和参数都是引用。
console.log(o);