按引用传递JavaScript对象

按引用传递JavaScript对象,javascript,Javascript,请阅读下面代码中的注释,了解我在尝试什么 问 预期输出:根据JavaScript中的pass-by-reference机制,objOne预计会在最后记录{},因为objTwo是用{}初始化的 var objOne = { x: 1, y: 2 }; var objTwo = objOne; // change the x vlaue to 2 by objTwo objTwo.x = 2; // Change the value of key x in objOne as well

请阅读下面代码中的注释,了解我在尝试什么 问

预期输出:根据JavaScript中的pass-by-reference机制,
objOne
预计会在最后记录
{}
,因为
objTwo
是用
{}
初始化的

var objOne = {
  x: 1,
  y: 2
};

var objTwo = objOne;

// change the x vlaue to 2 by objTwo
objTwo.x = 2;

// Change the value of key x in objOne as well - pass by reference mechanism
console.log(objOne); // { x: 2, y: 2 }

/*** Pass by reference is understood in code, above this comment ***/

// Now what if objTwo initialized with empty object
objTwo = {};

console.log(objOne); // { x: 2, y: 2 } but expected output = {}

// As per pass by reference mechanism. objOne is expected to log {}, because objTwo was initialized with {}.
当你评估

objTwo = {};
Javascript将其解释为将objTwo重新分配给新的文本空对象,并保留其旧值

如果要通过引用从objOne中删除密钥,可以使用
delete
关键字:

delete objTwo.x;  // also deletes the x property of objOne

JavaScript按引用传递是不同的,只要您更改对象的属性(如obj.x=1),对象就会被视为引用,但对象变量本身的赋值(obj=[])会将其视为基于值的变量。

objTwo={}的工作方式与您认为的不同。我通常建议将变量视为“指针”

objOne
objTwo
是两个完全不同的变量。当您执行
objTwo={}
,它所做的是将
objTwo
变量指向另一个对象。它不会改变
对象
变量

让我们想象一下:

var objOne = {
  x: 1,
  y: 2
};

// objOne -> { x: 1, y: 2 }

var objTwo = objOne;

// objOne -> { x: 1, y: 2 } <- objTwo

objTwo.x = 2;

// objOne -> { x: 2, y: 2 } <- objTwo (update object via objTwo variable)

objTwo = {};

// objOne -> { x: 2, y: 2 }, objTwo -> {}
var objOne={
x:1,
y:2
};
//对象->{x:1,y:2}
var objTwo=objOne;
//objOne->{x:1,y:2}{x:2,y:2}{x:2,y:2},objTwo->{

只有删除才能调用初始化状态

for(var i in objOne){
    delete objOne[i];
}
@纳拉比诺维茨说

  • Javascript总是按值传递,但当变量引用对象(包括数组)时,“值”是对对象的引用
  • 更改变量的值不会更改基础基元或对象,它只是将变量指向新的基元或对象
  • 但是,更改变量引用的对象的属性确实会更改基础对象

当两个变量指向同一个对象时,并不意味着它们现在神奇地“绑定”在一起


在您的例子中,
objTwo={}
只是将
objTwo
更改为指向您创建的新对象。

当您将一个变量分配给另一个变量时,并不是这两个变量现在都通过引用链接;你误解了“参考传递”在这里的意思

保存对象的变量不会“直接”保存对象。它所持有的是对一个对象的引用。当您将引用从一个变量分配到另一个变量时,您正在复制该引用。现在,两个变量都包含对对象的引用。通过该引用修改对象会更改包含该对象引用的两个变量的对象


当您为其中一个变量指定一个新值时,您只是在修改该变量所持有的值。变量现在不再保存对对象的引用,而是保存其他内容。另一个变量仍然保留对原始对象的引用,赋值根本没有影响它。

我同意接受的答案,这只是一些代码来支持它

let objOne = {x: 1, y: 2};
let objTwo = objOne; // referencing to same thing

objTwo.x = 2;
console.log(objOne, objTwo); // output {x:2, y:2}, {x:2, y:2}

let objThree = {};
objTwo = objThree; // notice this. Same as "objTwo = {}", except now you have objThree as initial reference
console.log(objOne, objTwo, objThree); // output {x:2, y:2}, {}, {}


通过更改objTwo引用或添加完整的新值(如问题示例所示),您可以很容易地注意到发生了什么。

这就是通过引用传递的工作原理。在这里,objTwo指的是objTwo,因此无论您对objTwo做什么,在案例1中,
objOne
objTwo
都指同一个对象。因此,可以通过它们中的任何一个来更改
x
。重新初始化
objTwo
意味着它不再引用同一个对象。这不会导致所有其他现有引用变成{},而是引用的对象,而不是变量;发生的情况是,我更改为空object.JavaScript的引用根本没有“passbyreference”,句号。JavaScript是一种纯粹的传递值语言。passbyreference在计算机编程中有一个特殊的含义:它将变量的引用传递到函数中。JavaScript从来不会这样做。赋值不会更改对象,它会更改变量
obj
“您误解了“按引用传递”在这里的意思”我想借此机会告诉他们JavaScript根本没有按引用传递。@jpmc26否。如果您赋值的不是对象,就不会有“引用”不再变量所持有的值是一个引用,但该变量也可以持有其他值。@Caleth:这纯粹是传递值。是,该值可以是对象引用。对象引用和其他任何引用一样都是值。是的,使用该值可以提供对象的引用语义,这是人们在说“按引用传递”时所关心的@Caleth:(如果你不
@
非作者的人,他们不会收到你的注释通知。)这不是按引用传递的意思,因此,如果你遇到这些人,请向他们解释。:-)通过引用是计算机科学界的一个术语。它指的是将对变量的引用传递到函数中。JavaScript不能做到这一点。要理解像JavaScript这样的语言中的对象引用,最重要的一点是它们只是值。