为何仅obj1.value被修改?JavaScript引用传递问题咨询
为什么只有
obj1.value被修改? 这事儿核心得搞懂JavaScript里参数传递的规则,还有对象引用的工作方式,我给你一步步拆解:
先理清楚初始的变量指向关系
咱们先看代码开头的变量声明:
var obj1 = { value: "first value" }; var obj2 = { value: "second value" }; var obj3 = obj2;
这时候内存里的情况是:
obj1拿着一个地址,指向内存中的第一个对象{value: "first value"}obj2拿着另一个地址,指向第二个对象{value: "second value"}obj3和obj2拿着同一个地址,所以它俩指向同一个对象
函数调用时的参数传递:按值传递(对象传递的是引用地址的副本)
当调用 change(obj1, obj2) 时,JavaScript的参数传递规则是按值传递。这里的“值”对于对象来说,就是它在内存中的引用地址:
- 函数内部的
obj1参数,是外部obj1所持有的引用地址的副本——也就是说,函数里的obj1和外部的obj1指向同一个对象 - 函数内部的
obj2参数,是外部obj2所持有的引用地址的副本——一开始也指向外部obj2对应的那个对象
看函数内部的两个操作
咱们逐个分析函数里的两行代码:
obj1.value = "asdasd"
这里不是给函数内部的obj1变量重新赋值,而是通过引用修改了它指向的对象的属性。因为函数里的obj1和外部的obj1指向同一个对象,所以这个修改会直接反映到外部的对象上,外部打印obj1.value自然就变成了"asdasd"。obj2 = "lol"
这里是直接给函数内部的obj2参数变量重新赋值——把它从原来的对象引用,改成了字符串"lol"。这时候函数内部的obj2已经和外部的obj2没有任何关系了,它不再指向原来的那个对象。外部的obj2还是拿着原来的地址,指向{value: "second value"},所以打印obj2.value还是原来的值。
一句话总结
- 如果函数参数是对象引用的副本,修改引用指向的对象的属性,会影响外部的对象(因为指向同一个东西);
- 但直接给参数变量重新赋值,只会修改函数内部的变量,不会影响外部的变量(因为只是副本变了,原引用没动)。
内容的提问来源于stack exchange,提问作者Sai Ram
相关产品推荐
相关产品推荐

