2013-05-25 51 views
-1
var i=0; 
var t={ 
    a:function(){ 
    this.timer=setInterval(this.b,30); 
    }, 
    b:function(){ 
    if(i++<1){ 
     console.log(this); 
    } 
    } 
}; 
t.a(); 

为什么我得到[circular object global]?我想'这个'是指对象t;SetInterval with javascript in javascript

我该怎么做?

而且我知道如何解决这个问题,下面的代码是正确的结果:

var i=0; 
var t={ 
    a:function(){ 
    var that=this; 
    this.timer=setInterval(function(){ 
     that.b(); 
    },30); 
    }, 
    b:function(){ 
    if(i++<1){ 
     console.log(this); 
    } 
    } 
}; 
t.a(); 
+3

所以,如果你知道如何解决这个问题......你为什么问? – migg

+1

@migg我想知道为什么:) – Fakefish

+0

请不要混淆* context *('thisArg')与[variable] * scope * – Bergi

回答

2

您必须要么使用Function.prototype.bind或​​重新分配背景下,作为一个所谓的这样功能丧失它的上下文到全球范围。这是最容易在下面的例子中

o = { // an object 
    foo: 1, 
    bar: function() { // function assuming `this` is `o` 
     return this.foo; 
    } 
}; 
f = o.bar; // function `f` loses scope of `o` 
o.bar(); // 1,   o.foo is defined 
f();  // undefined, window.foo is undefined 

观察这里是你的情况的解决方案的一些例子

// bind 
function scopedInterval(func, delay, context) { 
    return window.setInterval(func.bind(context), delay); 
} 
// or call 
function scopedInterval(func, delay, context) { 
    return window.setInterval(function() {func.call(context);}, delay); 
} 

在这些例子中,你会传递this作为第三个参数,即

this.timer = scopedInterval(this.b, 30, this); 

如果你不这样做,的setInterval上下文是window(我总是调用它作为window.setInterval所以我不会忘记这一点)

+0

谢谢,我明白 – Fakefish

+0

这并不能解释为什么。这是因为它是语言错误 – 2013-05-25 13:55:25

+1

@Geeo我无法给出答案的唯一原因是(正如你在评论中重复的那样),你会说“这是一种语言错误”。这是一个意见,虽然我同意_JavaScript_有一个愚蠢的定义,这个''应该如何在这些情况下工作,它可能“错误的人”,我不认为这是一个“错误”。 –

0

如克罗克福德在他的惊人的书中说:“的Javascript:好的部分”:

当一个函数是不是财产一个对象,然后它被调用为一个函数[这是setInterval的情况]。当一个函数被这个模式调用时,'this'被绑定到全局对象。这是该语言设计中的一个错误。如果语言设计正确,当调用内部函数时,'this'仍然会绑定到外部函数的'this'变量。这个错误的后果是一个方法不能使用内部函数来帮助它完成工作,因为内部函数不会共享方法对对象的访问,因为它的'this'被绑定到错误的值。 [然后他谈到了你找到的解决方法],

你是对的想知道为什么这不起作用,对我来说,所有其他答案都无法正确解决这个问题。事实上,这是一种无意义的事情,正如Crockford所说,这是语言设计中的一个错误,它可能会让人感到困惑。

+0

谢谢,我还没有读过那本书,我会在某个时候读完这本令人惊叹的书! – Fakefish

+0

Crockford的'this'不应该引用全局对象,但是我认为如果'this'指向函数实例化时在词法上封闭的范围内的任何东西都会引起各种奇怪。 – Pointy

+0

@点你能说说你为什么这么想吗? – 2013-06-02 17:04:46