0

我正在尝试使用属性初始化程序将箭头函数用作类的方法。但是在声明方法之前,它们是不可访问的。如果我更改声明它们的顺序,它会起作用。

是预期的行为还是 babel 转译

class SampleClass1 {
  method2 = this.method1();
  method1() {
    return "works";
  }
}

console.log((new SampleClass1()).method2); // Works

class SampleClass2 {
  method2 = this.method1();
  method1 = () => {
    return "works";
  }
}

console.log((new SampleClass2()).method2); // Error

下面的 url 是一个 babel repl 实例,我想演示的代码请参考它。

https://babeljs.io/repl/#?evaluate=true&presets=es2015%2Creact%2Cstage-0%2Cstage-2&experimental=false&loose=false&spec=false&code=class%20SampleClass1%20%7B%0A%20%20method2%20% 3D%20this.method1()%3B%0A%20%20method1()%20%7B%0A%20%20%20%20return%20%22works%22%3B%0A%20%20%7D%0A% 7D%0A%0Aconsole.log(%22(new%20SampleClass1()).method2%22)%3B%0Aconsole.log((new%20SampleClass1()).method2)%3B%0A%0Aclass%20SampleClass2%20% 7B%0A%20%20method2%20%3D%20this.method1()%3B%0A%20%20method1%20%3D%20()%20%3D%3E%20%7B%0A%20%20% 20%20return%20%22works%22%3B%0A%20%20%7D%0A%7D%0A%0Aconsole.log(%22(new%20SampleClass2()).method2%22)%3B%0Aconsole.log ((new%20SampleClass2()).method2)%3B

4

2 回答 2

1

是的,这是预期的行为。请记住,这个 ESnext 提案草案中的语法基本上是去糖化的

class SampleClass1 {
  constructor() {
    this.method2 = this.method1();
  }
  method1() {
    return "works";
  }
}

class SampleClass2 {
  constructor() {
    this.method2 = this.method1();
    this.method1 = () => {
      return "works";
    }
  }
}

很明显,您可以从构造函数调用原型方法,但不能调用尚未创建的实例属性上的方法。

于 2016-04-03T16:27:44.390 回答
0

我将尝试以不同的方式来解释它,上下文将是 Babel transpilation 和 ES2016。

赋值创建变量。

InSampleClass2 method1只是一个变量,它恰好有一个函数作为它的值。

class SampleClass2 {
  method2 = this.method1(); // variable
  method1 = () => {  // oops, variable because of assignment.
    return "works";
  }
}

考虑一下,因为构造函数没有构造一个包含方法的对象,而只有两个变量。

现在,由于您method1稍后定义,method2未定义。然后你尝试调用未定义的东西。

这就是错误消息的原因。

如果您()像这样删除:

class SampleClass2 {
  method2 = this.method1; // no longer an error
  method1 = () => {
    return "works";
  }
}

实例化时不会出错SampleClass2

为什么第一个案例有效?

class SampleClass1 {
  method2 = this.method1();
  method1() {
    return "works";
  }
}

这基本上是说将命名的函数method1放入原型中SampleClass1并在构建新对象时分配一个名为method2method[sic] 的返回值的变量method1

不要相信原型相关的东西。

在 Babel 中查看以下代码。

console.log(SampleClass1.prototype.method1) // function body
console.log(SampleClass2.prototype.method1) // nothing

如果我错过了什么或犯了错误,请告诉我。希望能帮助到你。:)

于 2016-04-08T04:31:07.027 回答