首页 > javascript的作用域问题

javascript的作用域问题

今天被javascript的作用域搞混了,请各位帮我看下这段代码

<script type="text/javascript" src="//cdn.bootcss.com/jquery/2.2.4/jquery.min.js"></script>
<script type="text/javascript">
    $(document).ready(function(){
        var test = function () {
            console.log('hello');
        }
        var i = 1;
        $.each([2], function() {
            console.log(i);
            setTimeout('test()', 1000);
        })
    })
</script>

这段代码提示ReferenceError: Can't find variable: test
但是当把$(document).ready(function()删掉或者把var test改成test,即不用var的时候,运行就正常了,可是变量i不管有没有var都是可以获取得到的,这是什么原因?


首先在我的记忆中setTimeout();这个东东的第一个参数是个函数,注意,是个函数。第二,变量不管有木有var这个东东其实在这里并不打紧,因为相当于是个全局变量。你不写他就默认在window作用域下,写了效果也一样。


这种用字符串表示的计时器,首先解析为可执行的表达式,然后再执行,而且是在全局作用域内执行,所以找不到 test你把"test()"换成test就可以了,注意不要加引号


setTimeout 的第 1 个参数如果不是函数,在 Node6 里会报错

TypeError: "callback" argument must be a function

在浏览器里不报错,不过估计是用 eval 执行的,所以做个实验

(function() {
    var test = function() {
        console.log("hello");
    };
    // setTimeout("test()", 1000);
    eval("test()");
})();

结果输出 hello,很正常。

考虑到你提到的问题,跟作用域有关,把代码稍改一下

(function() {
    var test = function() {
        console.log("hello");
    };
    // setTimeout("test()", 1000);
    window.eval("test()");
})();

报 test 未定义。所有运行如下

从上面实验可以说明:setTimeout 的第一个参数是文本的时候,是通过 window.eval() 执行的。这个时候由于你的 var test() 未定义在 windows 作用域,所以报未定义错误。如果不加 vartest() 是在全局(也就是 window 作用域)内定义的,就可以找到并执行。


这种调用函数的方法不建议使用的。就和不建议使用eval一样。
https://developer.mozilla.org...

如果把'test()'改成test就和i能访问到一个道理,访问的都是父级作用域的数据。当使用'test()'是引用的作用域类似全局作用域,然而你定义test函数是在ready的回掉函数作用域并不是全局作用域。所以你把var声明或ready去掉可以方位。

【热门文章】
【热门文章】