9

这样做更好吗,

asset.addEventListener("load", function () {
  this.emit({
    type: "load",
    asset: asset
  });
}.bind(this), false);

或者

var scope = this;

asset.addEventListener("load", function () {
  scope.emit({
    type: "load",
    asset: asset
  });
}, false);

绑定函数更好,还是将引用存储this在变量中?

4

4 回答 4

4

这实际上取决于许多因素。以下是一些注意事项:

  • 从历史上看,从创建的函数.bind()速度较慢。

  • 绑定this不能改变它的值,而变量可以。(猜你希望它不会在这里改变。)

  • 您将丢失元素引用,尽管您仍然可以通过event.currentTarget.


要考虑的另一种替代方法是让您的对象实现事件侦听器接口。这将允许您将对象本身作为处理程序传递,并将调用您handleEvent()提供的方法的实现。

然后该this值将自动成为您的对象。

所以如果你this是一个来自构造函数的对象,你可以这样做:

function MyCtor() {
    // your constructor
}

// This implements the `Event Listener` interface
MyCtor.prototype.handleEvent = function(event) {
          // ------v----should be "load"
    return this[event.type](event)
};

// This is the `load` handler
MyCtor.prototype.load = function(event) {
    this.emit({
      type: "load",
      asset: event.currentTarget
    });
};

然后像这样绑定处理程序:

asset.addEventListener("load", this, false);

现在您this在句柄事件中的值将是您的对象,因此您可以调用它的其他方法,既不.bind需要也不需要闭包变量。

于 2013-06-21T18:41:40.167 回答
2

我觉得第二种选择更好,只是为了防止任何混淆。的使用this一直是许多 JavaScript 问题的问题,所以当你可以避免它时,我认为你应该避免它。顺便说一句,这也是在像 Knockout 这样的库中完成的。

如果您想了解有关关键字的更多信息,这是对在不同上下文中可能具有this的各种不同值的一个很好的解释:http: //javascriptweblog.wordpress.com/2010/08/30/understanding-javascripts-this/this

于 2013-06-21T18:16:55.783 回答
0

第二个选项兼容更多的浏览器。IE 8 及更低版本不支持 bind() 函数,如果这对您很重要的话。

Mozilla 关于绑定的页面有一个用于绑定功能的 pollyfill。以我的经验,添加到内置对象的原型通常是个坏主意。所以第二个选项是“更好”——只要确保使用描述性变量名而不是“那个”或“范围”。使用通用名称可能会让人感到困惑,尤其是当您添加更多功能时。

于 2013-06-21T18:48:17.007 回答
-1

它们都没有,因为它们都创建了以后永远无法删除的匿名函数。

var scope = this;
var handler = function () {
  scope.emit({
    type: "load",
    asset: asset
  });
};

asset.addEventListener("load", handler, false);
于 2013-06-21T18:20:36.720 回答