好的[your_time_of_day],
今天我学习了 javascript (es6) 中的组合和工厂函数。我明白composition should be preferred over inheritance并且已经同意这一点(至少在 javascript 中)。然后,我意识到我应该使用组合的情况......
第一个问题:
有没有一种方法可以改变我复杂的继承结构,使类由函数组成,而无需使用数量可笑的装饰器?我是否错过了有关构图的一般内容(我感觉我错过了)?
情况
我有一个基类 AudioPlayer:
class BaseAudioPlayer {
public track;
protected seekBar;
public togglePlay() {
//
}
public seek(time) {
//some seek methods using this.seekBar
}
}
一些玩家类将从这里扩展,如下所示:
class MainAudioPlayer extends BaseAudioPlayer {
public loadTrack(track) {
//This is horrible
this.track = track;
}
public setSeekBar(seekBar) {
//This is horrible
this.seekBar = seekBar
}
}
请记住,实际上我在父类和子类中有很多方法,并且某些子类中有很多方法,而其他类则没有。当然,不涉及多重继承,但我发现在某些时候,多个相似的子玩家可能会出现这种情况(糟糕!)。
我可以使用许多装饰器,例如 @playable()
@seekable()
等,但后来我发现,最终,mixin 的数量会变得巨大。我想我也可以以类似的方式使用工厂函数,但会遇到同样的问题。
全面披露:我正在使用 Angular2,并大量削减了代码,以便保留有关使用哪种设计模式的讨论,而不是有关特定框架中的实现的讨论。
更新 1:
正如 @JocelynLecomte 评论的那样,我的问题可能不清楚。
MainAudioPlayer(和其他播放器)继承自 BaseAudioPlayer,因为所有音频播放器都必须具有
togglePlay
、seek
和一些其他方法(特定于 angular2,因此不是包含在这里)。目前继承自BaseAudioPlayer的类有3个:MainAudioPlayer、DetailAudioPlayer和CardAudioPlayer。将来可能会有更多,每个都有自己的具体方法。
使用继承来避免重复,所有播放器都是 BaseAudioPlayer。但是,所有玩家都有
togglePlay
和seek
方法。我想使用组合,因为我可以看到将来玩家可能没有
seek
方法或类似的方法。似乎使用组合会导致所有玩家类中出现大量样板代码,我想避免这种情况。
- 可以有许多装饰器(
@playable
、@seekable
) - 可以使用基础播放器服务(如 @amuse 的回答)并具有冗余方法。
- 可以有许多装饰器(
最佳答案
我认为如果你想重用基类中的基方法,你可能需要使用组合而不是继承(即:将 BasePlayerComponent 定义为 MainAudioPlayer 的属性):
class MainAudioPlayer{
constructor(){
this.basePlayerComponent=new BasePlayerComponent();
}
public loadTrack(track) {
//This is horrible
this.track = track;
}
public setSeekBar(seekBar) {
//This is horrible
this.seekBar = seekBar
}
public togglePlay() {
this.basePlayerComponent.togglePlay();
}
public seek(time) {
this.basePlayerComponent.seek(time);
}
}
关于javascript - 组合/继承/工厂 - 此案例的最佳模式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40895466/