将“this”引用到自定义变量

时间:2012-04-24 22:42:28

标签: javascript this

我正在做这样的事情:

var talkAPI = {
    init: function(){
        setInterval(function(){
            this.speak();
        },1000);
    },
    speak: function(){
         //Something else
    }
};

然而,我发现这不符合我的预期。所以我做了一些测试,我发现this中的setInterval指的是Window。这不是我想要的。那么我该如何重新推荐thistalkAPI?因为我不想这样做:

setInterval(function(){
    window.talkAPI.speak();    //Not so good
},1000); 

2 个答案:

答案 0 :(得分:5)

您需要保存原始this以便在回调中使用

init: function() {
    var self = this;
    setInterval(function(){
        self.speak();
    },1000);
},

答案 1 :(得分:2)

问题在于,this完全由如何调用函数定义,而不是定义它的位置(就像在其他语言中使用该关键字一样)。因此,setInterval调用您提供的函数的方式,this未设置为任何特定的(因此默认为全局对象,在浏览器上为window)。更多信息:You must remember this

使用您引用的代码,您有两种选择:

  1. 正如Kolink所评论的那样,由于您的对象是单身,并且init函数会关闭talkAPI变量,因此没有任何理由您不能只使用talkAPI

    var talkAPI = {
        init: function(){
            setInterval(function(){
                talkAPI.speak();    // <=== Only change is here
            },1000);
        },
        speak: function(){
             //Something else
        }
    };
    
  2. 对于单例和构造函数等创建的对象,更通用的答案是保留thisas described by JaredPar的值:

    var talkAPI = {
        init: function(){
            var self = this;        // <=== Create a variable to close over
            setInterval(function(){
                self.speak();    // <=== Use it
            },1000);
        },
        speak: function(){
             //Something else
        }
    };
    
  3. 在这两种情况下,函数都有一个持久的,实时的链接到它们关闭的符号,这就是他们可以使用它们的原因。以这种方式绑定到它们的数据的函数称为闭包。更多信息:Closures are not complicated