ES6 - 重新绑定 class 方法

ES6 - Rebinding class methods

我目前正在试验 ES6 classes,我遇到了这个我不完全理解的问题。我想制作一个 class ,它通过给它一个函数来初始化。 class 有一个运行该函数的方法,但具有任何给定的上下文。我试图用这样的方法来做到这一点:

class MyClass {
  constructor(action) {
    this.action = action;
  }
  run(context, n) {
    this.action.call(context, n);
  }
}

// instantiate my class with a function that uses 'this' to log a given number
let a = new MyClass((n) => {
  this.log(n);
})

// calls the run method of my class, giving console as the context and 1 as n.
a.run(console, 1);

我希望这段代码会导致 1 被记录到控制台。但是,我得到的是 TypeError。

我想我对 classes 和上下文绑定在 ES6 中的工作方式有一些误解。谁能帮帮我?

编辑

好吧,这是关于箭头函数和函数声明之间区别的很好的一课。感谢您的回答!

问题出在箭头函数的工作方式上。

箭头函数将 this 绑定到它们的词法环境:

let obj = {
  a: 1,
  init() {
    this.log = () => console.log(this.a);
  }
};

obj.init();
obj.log();

// And the `this` value cannot be changed
obj.log.call({ a: 500 });

要修复您的代码,只需使用正则函数表达式定义 action

class MyClass {
  constructor(action) {
    this.action = action;
  }
  run(context, n) {
    this.action.call(context, n);
  }
}

let a = new MyClass(function(n) {
  this.log(n);
})

a.run(console, 1);

你对箭头函数的使用破坏了东西

let a = new MyClass((n) => {
  this.log(n);
});

相同
let _this = this;
let a = new MyClass(function(n) {
  _this.log(n);
});

因为箭头函数查找其父级的作用域。你应该使用一个正常的函数作为

let a = new MyClass(function(n) {
  this.log(n);
});