是否有一种设计模式可以将方法注入到类中?

发布于 2024-10-15 06:16:51 字数 283 浏览 1 评论 0原文

我有一组可以协同工作的类(我正在用 javascript 进行编码)。

有一个父类和许多由父类实例化的子类。我有许多这些类的客户,每个客户都需要向父类或子类添加一个或多个方法。

我不是让每个客户端都从这些类继承(这是可行的,但由于子类而变得混乱),而是让这些客户端在实例化主类时将函数传递到父类中。

主类动态创建方法,客户端可以调用这些方法,就像它们一直存在一样。

我的问题是:

  1. 这样做明智吗?
  2. 我正在做的事情的设计模式是什么?

I have a set of classes that work together (I'm coding in javascript).

There is one parent class and a number of child classes that are instantiated by the parent class. I have a number of clients of these classes that each need to add one or more methods to the parent or child classes.

Rather than having each client inherit from these classes, which is doable but messy because of the child classes, I am having these clients pass functions into the parent class when they instantiate the main class.

The main class creates the methods dynamically and the clients can call the methods like they were there all along.

My questions are:

  1. is this a sensible thing to do?
  2. what would the design pattern be for what I am doing?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

〆一缕阳光ご 2024-10-22 06:16:51

策略模式适用于在运行时获取“策略”的情况。可能适用于此。在这种情况下,策略是一个符合行为的类,即具有“执行”等方法。

装饰器模式也可能适用。它也是一种运行时模式,但增强了它在方法级别修饰的类。

因此,如果您动态选择一个类,则策略模式很好,如果您仅在运行时更改方法实现,则装饰器模式很好。

(我在 ircmaxell 的许可下采用了这个答案的装饰器部分)

The strategy pattern is for situations where you get your 'strategy' at runtime. might be applicable here. Strategy in this case is a class that conforms to a behavior, i.e. has a method like 'execute' or whatever.

The decorator pattern also might apply. It is also a runtime pattern, but augments the class it is decorating at the method level.

So the Strategy pattern is good if you are choosing a class dynamically, and Decorator is good if you are only changing out the method implementation at runtime.

(I took the decorator part of this answer with permission from ircmaxell)

茶底世界 2024-10-22 06:16:51

我必须承认模式不是我的“事”——但你可以在 javascript 中完全做你想做的事。这就是所有框架如何完成“扩展”子“类”之类的事情(JavaScript 中没有类)。

如果你在纯javascript世界,你想使用:

foo.prototype.bar = function() {};

所以你可以在任何foo上调用bar,并且bar只存在于内存中一次 - 即通过每个 foo 对象在内存中引用同一个函数。因此,请小心您可能在该范围之外引用的任何变量。

每个库都有自己的插件架构来实现大致相同的目标(并且它们负责原型中的一些混乱/危险)

I must admit that patterns aren't my "thing" - but you can do exactly what you want to in javascript. It is how all of the frameworks accomplish that sort of things "extending" child "classes" (there are no classes in javascript).

If you are in the pure javascript world, you want to use:

foo.prototype.bar = function() {};

So you can call bar on any foo, and bar only exists in memory once - that is the same function is referenced in memory through every foo object. So be careful with any variables you might be referencing outside that scope.

Each library has their own plugin architecture to accomplish roughly the same goal (and they take care of some of the messiness/danger in prototype)

半葬歌 2024-10-22 06:16:51

您应该提供一些代码,以便我们能够准确地了解您正在谈论的内容。

因为您没有:我只能猜测您没有使用原型。原型将是“面向对象”JavaScript 的“正确”设计模式。

当您在 JavaScript 中将函数/属性/任何内容添加到对象的原型时,所有实例(无论新的还是旧的)都会在其原型上接收函数/属性/任何内容。

在 JavaScript 中扩展原型非常简单,并且永远不应该变得混乱。如果确实如此,则可能意味着您将其过于复杂化了。

You should provide some code, so that we can get a feel for what exactly you're talking about.

As you haven't: I can only guess that you're not making use of prototypes. Prototypes would be the "correct" design pattern for "object-oriented" JavaScript.

When you add a function/property/whatever to the prototype of an object in JavaScript, all instances, new and old receive the function/property/whatever on their prototype.

Extending prototypes in JavaScript is very simple, and should never become messy. If it does, it probably means you're over-complicating it.

稳稳的幸福 2024-10-22 06:16:51

正如 hvgotcodes 所说,您正在描述策略模式,针对您的特定情况执行此操作的方式不是使用原型(从而影响类的所有对象。)

而是提供一个接受函数作为其值的成员。

例如

function MyClass() {
    this.myFunction = defaultFunction;

    this.defaultFunction = function() {
       // do something by default.
       alert("using default");
    }

    this.doFunction = function() {
       // something that calls myFunction.
       this.myFunction();
    }
}

---8< snip --------

// later on...

t = new MyClass();
t.doFunction(); // output 'using default'
t.myFunction = function(){ 
   // do something specific with this instance, when myFunction is called. 
   alert("customized for this instance.");
}
t.doFunction(); // output 'customized for this instance.'

As hvgotcodes says, you are describing the Strategy Pattern, the way you would do this for your specific case, is not to use prototypes (thereby affecting all objects of your class.)

Instead you'd provide a member that accepts a function as it's value.

e.g.

function MyClass() {
    this.myFunction = defaultFunction;

    this.defaultFunction = function() {
       // do something by default.
       alert("using default");
    }

    this.doFunction = function() {
       // something that calls myFunction.
       this.myFunction();
    }
}

---8< snip --------

// later on...

t = new MyClass();
t.doFunction(); // output 'using default'
t.myFunction = function(){ 
   // do something specific with this instance, when myFunction is called. 
   alert("customized for this instance.");
}
t.doFunction(); // output 'customized for this instance.'
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文