我有一个带有类层次结构的Java包,比如A类,包含子类A1,A2,A3,......
对于特定的应用程序,我需要创建实现接口B的类(类型A)。这些新类将有一些共同点,所以我首先想到的是创建一个继承自A并实现B的基类C ,我的新类C1,C2,C3,...将继承自C。但是,其中一些类Ci需要存在于其中一个Aj中的功能,并且通过这种方法我需要重新实现这样的功能(功能未在A中定义)。对于一些Ci,我想继承各种Ai的行为,但同时继承C中所有Ci的共同行为。当然,Java不允许多重继承所以我不能做这直接。我当然不希望重新实现这么多东西只是因为MI不受支持,但我没有看到解决方法。有什么想法吗?
答案 0 :(得分:1)
你真的需要子类,还是只想重复使用代码?
听起来像是使用了Composite和可能的策略模式:
您的C类将包含A类和B类字段,并在适当时委托对它们进行调用。这为您提供了代码重用的所有优点,而没有继承的混乱(单个或多个)
答案 1 :(得分:1)
当他们第一次看到类层次结构的有用性时,每个人似乎都会注意到这个问题。问题源于班级中的正交问题。一些子类共享特征1和一些共享特征2.一些没有。有些人都有。
如果只有一个特征......(说,有些人有内部,所以他们可以填补。)...我们会没事的。创建一个中间子类来处理这些问题。一些子类实际上是中间类的子类。我们已经完成了。
但是有两个并且没有办法进行子类化。我认为多重继承是该问题的解决方案,但它增加了一定程度的复杂性并颠覆了思维的简单性,使层次结构类结构变得有用。
我发现最好使用子类化来解决它容易解决的问题。然后选择一种隔离和共享代码的方法,除了子类化。
一种解决方案是提取功能并将其移动到其他位置。然后所有的Aj和Ci都可以在那里调用它。优点是您不会复制和粘贴任何代码,如果它被破坏,它可以在一个地方修复。
一个代码可以进入基类A并获得一个名称,表明它只适用于某些孩子。使方法受到保护。然后从实际的类中调用它们。它丑陋但有效。
A
protected String formStringForSubclassesAjAndCi(String a, int b) {
return a + b;
}
Ci和Aj
public String formString(String a, int b) {
return formStringForSubclassesAjAndCi(a, b);
}
两个同样,您可以将共享代码放在某种辅助类中:
CiAjHelper
public static String formStringForSubclassesAjAndCi(String a, int b) {
return a + b;
}
Aj和Ci
public String formString(String a, int b) {
return CaAjHelper.formStringForSubclassesAjAndCi(a, b);
}
三第三种方法是将代码放入say,Aj,然后通过为每个Ci实例提供Aj实例并将常用函数委托给它来从Cj调用它。 (它仍然很难看。)
AJ
public String formString(String a, int b) {
return a + b;
}
CJ
private Aj instanceAj = new Aj();
public String formString(String a, int b) {
return instanceAj.formString(a, b);
}