我知道拥有钻石继承权被认为是不好的做法。但是,我有两个案例,我觉得钻石继承非常适合。我想问一下,你会建议我在这些情况下使用钻石继承,还是有其他设计可以更好。
案例 1:我想在我的系统中创建代表不同类型“动作”的类。这些动作按几个参数分类:
- 动作可以是“读”或“写”。
- 动作可以有延迟或无延迟(它不仅仅是 1 个参数。它显着改变了行为)。
- 动作的“流类型”可以是 FlowA 或 FlowB。
我打算有以下设计:
// abstract classes
class Action
{
// methods relevant for all actions
};
class ActionRead : public virtual Action
{
// methods related to reading
};
class ActionWrite : public virtual Action
{
// methods related to writing
};
class ActionWithDelay : public virtual Action
{
// methods related to delay definition and handling
};
class ActionNoDelay : public virtual Action {/*...*/};
class ActionFlowA : public virtual Action {/*...*/};
class ActionFlowB : public virtual Action {/*...*/};
// concrete classes
class ActionFlowAReadWithDelay : public ActionFlowA, public ActionRead, public ActionWithDelay
{
// implementation of the full flow of a read command with delay that does Flow A.
};
class ActionFlowBReadWithDelay : public ActionFlowB, public ActionRead, public ActionWithDelay {/*...*/};
//...
当然,我会遵守没有 2 个动作(从 Action 类继承)将实现相同的方法。
案例 2:我在我的系统中为“命令”实现复合设计模式。一个命令可以读、写、删除等。我也想有一个命令序列,也可以读、写、删除等。一个命令序列可以包含其他命令序列。
所以我有以下设计:
class CommandAbstraction
{
CommandAbstraction(){};
~CommandAbstraction()=0;
void Read()=0;
void Write()=0;
void Restore()=0;
bool IsWritten() {/*implemented*/};
// and other implemented functions
};
class OneCommand : public virtual CommandAbstraction
{
// implement Read, Write, Restore
};
class CompositeCommand : public virtual CommandAbstraction
{
// implement Read, Write, Restore
};
此外,我还有一种特殊的命令,“现代”命令。一个命令和复合命令都可以是现代的。成为“现代”会为一个命令和复合命令添加特定的属性列表(它们的属性大多相同)。我希望能够持有指向 CommandAbstraction 的指针,并根据所需的命令类型(通过 new)对其进行初始化。所以我想做下面的设计(除了上面的):
class ModernCommand : public virtual CommandAbstraction
{
~ModernCommand()=0;
void SetModernPropertyA(){/*...*/}
void ExecModernSomething(){/*...*/}
void ModernSomethingElse()=0;
};
class OneModernCommand : public OneCommand, public ModernCommand
{
void ModernSomethingElse() {/*...*/};
// ... few methods specific for OneModernCommand
};
class CompositeModernCommand : public CompositeCommand, public ModernCommand
{
void ModernSomethingElse() {/*...*/};
// ... few methods specific for CompositeModernCommand
};
同样,我将确保没有 2 个从 CommandAbstraction 类继承的类将实现相同的方法。
谢谢你。