[英]Why does my JS object incorrectly change when not assigning the object to a variable?
请向我解释这个现象。
this.testObject = { a: 1, b: { a: 3, b: { a: 78, b: null } } }; let g = this.testObject; while (gb) { g = gb; } gb = { a: 79, b: null }; console.log(this.testObject); // { a: 1, b: { a: 3, b: { a: 78, b: { a: 79, b: null } } } }
现在我决定坚持使用this.testObject
并删除g
:
this.testObject = { a: 1, b: { a: 3, b: { a: 78, b: null } } }; while (this.testObject.b) { this.testObject = this.testObject.b; } this.testObject.b = { a: 79, b: null }; console.log(this.testObject); // {a": 78,b": {a": 79,b": null}
这是怎么回事? 我的g
分配如何以这种方式影响这个 object?
在第一个片段中,如果我做了g=gb
那么我基本上是在为g
分配一个新值。 但是,如果我明确地这样做,那么结果不一样吗?
this.testObject = {a:1, b:{a:3,b:{a:78, b:null}}}; let g = this.testObject; while(gb){ g = {a:7777, b:null}; } gb={a:79, b:null}; this.testObject; // {a": 1,b": {a": 3,b": {a": 78,b": null}
我猜你希望这两个片段产生相同的结果。 但是代码并没有做同样的事情。
您在第一个示例中使用g
作为一种参考。 这意味着每次在 while 循环中设置g
时,您都不会以任何方式影响this.testObject
,因为您只是在“移动”引用。 但它仍然是一个引用,因此更改g
引用的 object 中的任何内容,您还将在this.testObject
中设置它,从而产生您在第一个示例中获得的结果。
在第二个示例中,您每次都在 while 循环中替换this.testObject
。 因此设置this.testObject = this.testObject.b
将移除外部 object,导致this.testObject
来自:
{ a: 1, b: { a: 3, b: { a: 78, b: null } } }
至:
{ a: 3, b: { a: 78, b: null } }
并且由于this.testObject.b
不是 null,因此您再次重复此操作,使this.testObject
变为:
{ a: 78, b: null }
最后,将this.testObject.b
设置为新的 object,覆盖之前的 null 值。 这将导致您在第二个示例中获得 output。
通常在回答这些问题时,人们会在它们之间绘制方框和箭头来表示指针,但我很懒,所以让我们考虑一个简单的虚拟机。 这台机器可以在 memory 块及其编号(又名“指针”)上运行。 共有三种操作:
$number
)就这台机器而言,您的第一个片段将转换为:
// this.testObject = { a: 1, b: { a: 3, b: { a: 78, b: null } } };
allocate: $1 = {a: 78, b: null}
allocate: $2 = {a: 3, b: $1}
allocate: $3 = {a: 1, b: $2}
write: this.testObject = $3
// let g = this.testObject;
write: g = $3
// while (g.b) { g = g.b; }
write: g = $3.b // first pass, g is now $2
write: g = $2.b // second pass, g is now $1
// g.b = { a: 79, b: null }
allocate: $4 = { a: 79, b: null }
write: $1.b = $4
// console.log(this.testObject);
read: $3 ==> {a: 1, b: $2}
read: $2 ==> {a: 3, b: $1}
read: $1 ==> {a: 78, b: $4}
read: $4 ==> { a: 79, b: null }
基本上,每个{...}
都是一个“分配”操作,每个分配都是一个“写”, console.logs
是“读”。 尝试将你的其他片段“翻译”到这台机器上,你会看到实际发生了什么。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.