1

如果我们有以下类(一个简化的例子):

function MyClass() {
    this.greeting = "Where is the ice cream?";
}

MyClass.prototype.talk = function() {
    console.log(this.manners(this.greeting));
}

MyClass.prototype.manners = function(phrase) {
    return "I beg your pardon. " + phrase;
}

然后我们尝试通过 ajax 发送它,如下所示:

var c = new MyClass();
$.ajax({
    data : c,
    url : "ajax.php",
    dataType : "json",
    type : "post"
});

我得到一个例外MyClass.prototype.talk,说“this.manners不是函数”。我得到这个异常的原因是,由于某种原因,ajax 调用强制调用所有方法MyClass,使用 a thisof Window(而不是实例MyClass)。

因此,我有几个问题:

  • 为什么 ajax 调用强制使用 Window for 调用类的每个方法this
  • 以我的方式manners打电话不合适吗?talk我应该设置this自己吗?(不确定在这种情况下怎么可能)

总的来说,我对如何以及何时使用applyand仍然一无所知call,所以整个话题对我来说非常混乱。每当我在过去遇到此类问题(例如,在事件处理中)时,我都会求助于var that = this;变通方法,但我认为是时候更深入地了解该主题了。此外,无论如何,该修复程序在这里不起作用。

4

3 回答 3

1

编辑:虽然方法是正确的,但原型不继承局部变量,stingify 看起来是最好的路线。

回答问题: 1. 'this' 总是反映当前上下文,AJAX 诉诸全局范围,从而产生窗口。2.合适吗?可能不是。我倾向于以下列方式使用它:

var c = new MyClass();
c.greeting = 'You ate all the ice cream!';
c = c.manners(c.greeting);
$.ajax({
    data : c,
    url : "ajax.php",
    dataType : "json",
    type : "post"
});

下面的建议在这种情况下不起作用:

在我的头顶上;在 myClass() 中显式设置“this”

var _that = this;

...在原型方法中用 _that 替换“this”

范围在 AJAX 请求期间丢失并恢复为窗口。在类的顶部定义 _that = 'this' 始终确保范围保持不变。

于 2013-09-29T19:15:23.563 回答
1

我认为你需要序列化你的数据。

data : JSON.stringify(c),

现在似乎发布:http: //jsfiddle.net/JvPym/

this我认为or没有任何问题window

于 2013-09-29T19:16:07.203 回答
0

关于 javascript 要了解的一件事是它没有类。Javascript 有对象和函数(函数就是对象)。

this变量附加到函数,并遵循“调用模式”。this取决于您调用函数的方式。所有函数对象都有一个callandapply方法来执行它们被调用的函数对象。这些方法的第一个参数指定在this函数执行期间将作为上下文引用的对象,但是如果它为 null 或未定义,window则使用全局对象。

克服这个问题的最好方法是在函数中创建一个内部变量,以便this稍后在正确的上下文中引用。下面是一个如何重写它的例子:

function MyClass() {
        var _self = this;  
        this.greeting = "Where is the ice cream?";


    this.talk = function() {
        console.log(_self.manners(this.greeting));
    }

    this.manners = function(phrase) {
        return "I beg your pardon. " + phrase;
    }
}

注意_self如果用于引用正确的上下文。在您的函数中,您只会引用_self而不是this.

于 2013-09-29T19:40:06.857 回答