1 function hehe(o,oo){ 2 o = 'xoxo' 3 oo.ins.name = 'zhangmingzhi;' 4 } 5 var obj = { 6 ins:{ 7 8 } 9 } 10 hehe(obj.ins,obj); 11 console.log(obj);
情况1,传入参数为oo,为一个引用类型的时候,参数修改的值会体现在外部 即obj中。
情况2,传入参数为o,为一个引用类型,参数修改的值在外部obj.ins体现不出来
根据情况2的猜想:可能是obj在栈上的引用地址可能只是储存了obj 而ins则在堆上真实的地址上。如果把obj.ins作为参数传递进去的话,那么操作這个传入的值就是没有栈地址的值,自然在方法里修改的就体现不到外面的obj对象中了
PS:以上只是猜想,回去翻翻书。。
20日更新翻书后的结果:
基本点1:引用类型的赋值 如 var a = {};var b = a; 这种,a 赋值给了b,a、b在stack上的值是相同的,值为指向heap中真实值得地址,stack中的值可以被称为指针。
基本点2:如果把b的值重新赋值,值的类型为引用,值类型都行,那么修改的是stack上的值,所以,就不会得到修改了b的值(指向heap上值得地址即指针)后同时修改了a的指针指向heap上的值。
基本点3:如果存在以下代码:
var me = { skill:{ js:'poor', css:'soso' }, attr:{ age:24 }, name:'zmz' } var o = me; var _attr = me.attr; //修改stack中的指针; o = {}; _attr = ''; //这里针对“me”修改的所有值都是无效的,如果o的值为一个值类型而不是对象的话。 o.name = 'zhangmingzhi'; _attr.height = '174mm'; console.log(me);
_attr 赋值为me的属性对象 attr,那么所有对_attr进行属性操作的话,me就会有反应,应为_attr和me.attr 都指向同一个heap地址。假如直接对_attr进行赋值就会出现基本点2的情况。
基本点4:把引用类型当作参数传递进去。采用的还是值传递的方式,如下图代码:
var me = { attr:{ age:24, height:'222' }, name:'zmz' } function test(o){ o = 123; o.name = 'zhangmingzhi'; } test(me); console.log(me)
运行test方法,传入参数为一个对象me,在方法内调用参数o,这时候o的值和me的值一样,都是指向heap中的值,即指针相同。这和基本点1是一致的,假如我们把参数o的值重新赋值一下,那么o的值也就是指针(假如赋值的值是一个对象的话)那么就和基本点2、3一样。
基本点5:所有的引用类型都和以上4个基本点一致,如 Array,Function。