Javascript backbonejs函数未定义
我遇到一个未定义的函数 我得到键值对并在forEach上执行函数 结构Javascript backbonejs函数未定义,javascript,backbone.js,Javascript,Backbone.js,我遇到一个未定义的函数 我得到键值对并在forEach上执行函数 结构 var AppView = Backbone.View.extend({ initialize: function() { this.render(); }, render: function() { this.$el.html("Hello World"); this.one(); }, one: function() { this.two(); }, two:
var AppView = Backbone.View.extend({
initialize: function() {
this.render();
},
render: function() {
this.$el.html("Hello World");
this.one();
},
one: function() {
this.two();
},
two: function() {
var object = {
"labname4": "423",
"Path": "4",
"X": "4"
};
console.log('two');
Object.keys(object).map(function(objectKey, index) {
var value = object[objectKey];
this.three();
});
},
three: function() {
console.log('three');
},
});
var appView = new AppView();
console.log("done");
使用:
- jquery/1.7.2
- 下划线.js/1.3.3
- 主干。js/0.9.2
Object.keys(object).map(function(objectKey, index) {
var value = object[objectKey];
this.three();
});
在这里,this.three()
,this
不再引用您的对象,因为它位于嵌套函数范围内,并且没有在其上定义方法three()
有两种可能的解决方案:
a) 使用clojure
代替嵌套函数。您可以编写相同的代码,如下所示:
Object.keys(object).map((objectKey, index) => { // note the arrow and no 'function' keyword
var value = object[objectKey];
this.three();
});
clojure
保持在当前范围内,因此this.three()
将起作用,函数
另一方面定义了它自己的范围
b) 如果希望在特定范围内执行,可以绑定函数
,如:
Object.keys(object).map(function(objectKey, index) {
var value = object[objectKey];
this.three();
}.bind(this)); // note '.bind(this)'
这样,函数将使用您当前的作用域,而不是创建一个新的作用域。
这两种方法都是有效的,由用户选择一种,我个人更喜欢clojures
,因为调用Object.keys(Object.map)时会更改范围。这也会更改,因此您无法使用它访问原始值。将其别名设置为允许您仍然访问此的原始值。您的代码将像这样运行
var AppView = Backbone.View.extend({
initialize: function(){
this.render();
},
render: function(){
this.$el.html("Hello World");
this.one();
},
one: function(){
this.two();
},
two: function(){
var that = this;
var object = { "labname4": "423",
"Path": "4",
"X": "4"};
console.log('two');
Object.keys(object).map(function(objectKey, index) {
var value = object[objectKey];
that.three();
});
},
three: function(){
console.log('three');
},
});
var appView = new AppView();
console.log("done");
编辑1var=this vs bind
在我看来,bind肯定有它的位置。例如,当你在一个变量中有一个函数,你想把它附加到一个特定的变量上
也就是说,在嵌套匿名函数的情况下,我认为使用var=this;简单明了,与使用.bind相比,需要更少的脑力计算。例如,假设我们有两个嵌套函数:
function foo() {
return (function() {
doSomething((function() {
return this.name; // what is `this` again?
}).bind(this));
}).bind(this);
}
vs
当然,因为这是一个风格问题,“心理会计”的问题将因人而异。但对我来说,考虑到Javascript的this的符号,我认为this=当您有嵌套回调时,这很容易理解。将this.three()
移动到对象.keys().map()函数之外谢谢Kevin,Ante Jablan Adamović更精确,因为需要嵌套数据。您的代码毫无意义,显而易见的解决方案是删除所有无用的样板文件。如果没有明确的命令,我们只能告诉您使用bind
,即使这样,它也是一个副本。此外,请升级到最新的主干,并使用下划线,因为您已经在加载它<代码>\每个(对象、函数(值、键){…},这个)
您可以直接传递上下文。可能被愚弄的人知道,var that=this
是老办法,相反,使用clojure
或bind
?@antejablandamović请阅读编辑1@V.S.V你所做的是很糟糕的练习,嵌套多个回调只会增加不必要的复杂程度,使代码无法读取。使用bind
稍微有点帮助,但不是最佳解决方案,而clojures
只是保留范围而不添加任何额外代码,此外,它们实际上减少了代码量,因此远远优于其他任何东西,并使代码更干净、更可读。虽然您认为bind
比var that=this
更好,但=>
不是a,而是an,在这个问题上与之无关,因为它不使用ES6。。。
function foo() {
var that = this;
return (function() {
doSomething((function() {
return that.name; // `that` is easy to know because its defined
})
})
}