简体   繁体   English

在构造函数中的任何内容之前运行链接方法?

[英]Run chained method before anything in constructor?

I have this simple class: 我有这个简单的课程:

 class Foo { constructor() { this.init(); return this; } init() { this.onInit(); } onInit(callback) { this.onInit = () => callback(); return this; } } new Foo().onInit(() => console.log('baz')); 

It's obviously flawed, because it will call init before the onInit method is able to define the onInit property/callback. 这显然是有缺陷的,因为它将在onInit方法能够定义onInit属性/回调之前调用init

How can I make this work without change the interface? 如何在不更改界面的情况下完成这项工作?

How can I make this work without change the interface? 如何在不更改界面的情况下完成这项工作?

You can't, the interface is inherently flawed. 您不能,界面天生就有缺陷。 That's really the answer to your question. 这确实是您问题的答案。


Continuing, though, with "what can I do instead": 不过,继续“我该怎么办”:

If you need to have a callback called during initialization, you need to pass it to the constructor, not separately to the onInit method. 如果需要在初始化期间调用回调,则需要将其传递给构造函数,而不是单独传递给onInit方法。

class Foo {
  constructor(callback) {
    this.onInit = () => {
        callback();  // Call the callback
        return this; // Chaining seemed important in your code, so...
    };
    // Note: Constructors don't return anything
  }
}

new Foo(() => console.log('baz'));

In a comment you've said: 在评论中,您说过:

I see your point, the fact is that my library is new Something().onCreate().onUpdate() 我明白你的意思,事实是我的图书馆是new Something().onCreate().onUpdate()

It sounds like you might want to adopt the builder pattern instead: 听起来您可能想改用构建器模式

class Foo {
    constructor(callbacks) {
        // ...use the callbacks here...
    }
    // ...
}
Foo.Builder = class {
    constructor() {
        this.callbacks = {};
    }
    onCreate(callback) {
        this.callbacks.onCreate = callback;
    }
    onUpdate(callback) {
        this.callbacks.onUpdate = callback;
    }
    // ...
    build() {
        // Validity checks here, do we have all necessary callbacks?
        // Then:
        return new Foo(this.callbacks);
    }
};

let f = new Foo.Builder().onCreate(() => { /*...*/}).onUpdate(() => { /*... */}).build();

...although to be fair, a lot of the advantages (though not all) of the builder pattern can be realized in JavaScript by just passing an object into constructor directly and doing your validation there, eg: ...虽然公平地说,只要将对象直接传递到constructor并在其中进行验证,就可以在JavaScript中实现构建器模式的许多优点(尽管不是全部)。

let f = new Foo({
   onCreate: () => { /*...*/},
   onUpdate: () => { /*...*/}
});

Assuming that onInit is supposed to be some sort of hook to be called synchronously whenever an object is instantiated, you can't solve this on the instance level. 假定onInit应该是某种在实例化对象时同步调用的钩子,那么您将无法在实例级别解决此问题。

You can make onInit a static function, like so: 您可以将onInit静态函数,如下所示:

 class Foo { constructor() { // whatever Foo.onInit(); } static onInit() {} // empty default } Foo.onInit = () => console.log('baz'); // Override default with your own function const f = new Foo(); const f2 = new Foo(); 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM