如何在 Javascript 中的 class 定义(外部)中定义原型方法?

How to define prototype method inside class definition (externally) in Javascript?

我有一个 class 声明,其中有很多方法。

是这样的:

class Foo {
  constructor() {
    // ...code
  }
  config() {
    // ...code
  }
  theme() {
    // ...code
  }
  register() {
    // ...code 
  }
  render() {
    // ...code
  }
  write() {
    // ...code
  }
}

我想将源代码分开,以便于管理和阅读。

有没有一种方法可以在 class 本身内动态地将方法分配给 class?

我想做类似的事情:

function bar(value) {
  if (value) {
    this.baz = 'baz'
    return this
  }
}

class Foo {
  constructor() {
    // ...code
  }
  new bar() // Would reference function above ^ (not valid)
}

我知道这是无效或不正确的,但因为 class 语法会自动创建一个名为 bar() 的 属性 并将其绑定到 Foo 的原型,我可以'没想到你会怎么做,也许功能不存在。

我能想到的最接近拆分代码的方法是扩展 class 但这似乎有点冗长。

class Bar {
  bar() {
    if (value) {
      this.baz = 'baz'
      return this
    }
  }
}
class Foo extends Bar {
  constructor() {
    super()
  }
}

bar() 现在在 Foo 的原型中。

如果需要,此方法也几乎无法控制创建别名,而且更难明确 Foo class.

中可用的方法

有没有更好的方法?

我可以想到两种添加外部函数作为自己的属性的方法:

  1. 在class的构造函数中将其设置为this的属性。
  2. 设置为class的public属性,这是proposal.

缺点是,所有实例都不会共享同一个函数对象,因为它变成了自己的属性。自己的属性用于保存状态而不是函数。

prototype中添加,也就是ES6class中方法的添加处,让所有实例共享同一个函数对象。您必须将其添加到 classprototype 属性。这是因为 classfunction 构造函数的语法糖,每个函数都有一个 prototype 属性,它由 class 的所有实例继承。

class Foo {
  constructor() {
    // ...code
    this.bar = bar; //becomes own property
  }
  
  //As a public field, becomes own property
  baz = baz;
  
}
function bar(){
  console.log("from bar");
}
function baz(){
  console.log("from baz");
}
function foobar(){
 console.log("from foobar");
}

const foo = new Foo();
foo.bar();
foo.baz();
//Set it directly on the prototype prop of the Class
Foo.prototype.foobar = foobar; 
foo.foobar();

Also, I presume there isn't a way to set a prototype of a class inside the class definition itself?

根据您在评论中的问题,是的,您可以在 class 定义本身内部的 class 原型中设置函数:

function bar(){
  console.log("bar in prototype");
  console.log("accessing data from this: ", this.data);
}

class Foo{
 constructor(){
   this.data = "data"
   Foo.prototype.bar = bar;
   Foo.prototype.thisBar = bar.bind(this);
 }
 //methods are added in prototypes
 baz(){
  console.log("baz in prototype");
 }
}

const foo = new Foo();
foo.bar();
foo.baz();
//accessing from prototype, here this is global context and will print undefined
Object.getPrototypeOf(foo).bar();
//this is bound so always refers to the instance
Object.getPrototypeOf(foo).thisBar();
//same for methods in es6
Object.getPrototypeOf(foo).baz();

对于静态方法,只需将其设置为 class 的 属性 或将其设置为 public static 属性.

class Bar{
  constructor(){
    //some logic
  }
  static baz = baz;
}
function foo(){
  console.log("from foo");
}
function baz(){
  console.log("from baz");
}
Bar.foo = foo;
Bar.foo();
Bar.baz();