javascript - 大家帮忙看下这个函数错误出在哪里了
阿神
阿神 2017-04-11 12:36:07
[JavaScript讨论组]
var obj = {
  hello: function(n) {
    return obj.hello(n-1) + n;
  }
}
var obj2 = {hello: obj.hello};
obj = {};
console.log(obj2.hello(3));

阿神
阿神

闭关修行中......

全部回复(5)
ringa_lee

这是典型的引用丢失问题,两个对象引用了相同的函数,但函数引用自身的时候只是通过其中的一个对象,当obj置为空对象时,obj2对象的匿名函数仍然存在,但是obj1的属性已经不存在了,而这时再通过原有的obj.hello属性引用进行递归调用自身时,就会出现严重的问题。
解决方案建议将匿名函数的obj1显式引用改成this(函数上下文),这样obj2.hello()的this对象就是obj2,如此便可解决问题。
或者使用内联命名函数,将obj1对象定义如下:

var obj1 = {
  hello: function js(n) {
    return js(n-1) + n;
  }
}
天蓬老师

因为你改变了obj的引用,所以在hello函数里面的引用的obj是那个新的obj
这个新的引用当然没有hello函数,自然就会报错。

但是,必须要注意的是,此时obj2引用的那个hello还存在。

巴扎黑

obj已经赋值为空对象了,obj2里的引用的obj.hello自然也不存在了。

大家讲道理

1.重新赋值obj对象了,新对象obj上没有hello()方法;
2.即使没有这段,你的hello()会栈溢出的,因为这是一个递归函数,就是不停地调用自己,n就侧漏了~~

阿神

以下内容纯属个人拙见,如有不妥,望不吝赐教,必将感激不尽

此函数考察内容有俩点:
1、引用类型数据的引用规则;2、函数的递归
分别阐述:
1、引用类型的引用,存储的是个地址,所以复制也是地址的复制,最后多个变量指向同一个引用类型数据。

例:var obj={"a":1};         //obj存储的是json对象地址
    var obj2=obj;            //obj2和obj存储统一地址,指向同一json对象
    console.log(obj2["a"]);    //1
    obj={};                    //obj是新引用类型数据的地址,obj2存储的原地址还存在
    console.log(obj2["a"]==1);    //true

总结:引用类型的多次赋值,不会导致覆盖,只会改变为新的地址,指向新的引用类型数据
所以,上面朋友说得对,obj2.hello函数还存在,因为函数也是引用类型数据

这个函数存在是存在,但调用就会出错,因为其中用到了obj.hello(n-1);
用递归的arguments.callee(n-1)改进即可

2、递归问题:

    函数递归调用,要设置边界,否则无限递归,超过内存
   ![图片描述][3]
    最完美递归:
        function recursion(n){
            if(n==1)return 1;
            return arguments.callee(n-1)+n;
        }
    
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新 English
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号