在所有示例中,我都看到接口用于实现多态性。现在我们有以下带有抽象类的代码
AbstractClass parent = new Child();
一个常见的论点是多态性仅适用于接口而不适用于抽象类。
我认为他的意思是它们通常是用于 Java 多态性的接口。我看到很多人发现他的问题很傻,想要 URL。这就是我发现的。所以我的问题是在Java中使用多态性中的抽象类(如我的示例 - 因为多态性是非常广泛的定义)是一种好的/常见的做法?
在所有示例中,我都看到接口用于实现多态性。现在我们有以下带有抽象类的代码
AbstractClass parent = new Child();
一个常见的论点是多态性仅适用于接口而不适用于抽象类。
我认为他的意思是它们通常是用于 Java 多态性的接口。我看到很多人发现他的问题很傻,想要 URL。这就是我发现的。所以我的问题是在Java中使用多态性中的抽象类(如我的示例 - 因为多态性是非常广泛的定义)是一种好的/常见的做法?
使用符合合同的最通用的父级是一种很好的做法;如果接口定义了您需要的所有函数签名,则使用它们而不是实现该接口的抽象类。Bill Venners 与 Erich Gamma 讨论的《设计模式中的设计原则》一文进行了详细介绍。
它们的最佳用途之一是您在“孩子”之间有共同的行为。
你的界面
interface Drawable{
void paint();
}
具有通用代码的抽象类
abstract class AbstractRectangularObject implements Drawable{
public void paint(){
paintVertices();
//your code to fill body
}
//Abstract method that all subclases needs to implement
protected abstract void paintVertices();
}
你真正的子类
class Rectangle extends AbstractRectangularObject {
protected void paintVertices(){
//code to pain vertices
}
}
-
class RoundRectangle extends AbstractRectangularObject {
protected void paintVertices(){
//code to pain vertices
}
}
如果您有共同的功能和属性在子类之间共享,同时类本身太抽象而不能有实例,那么使用抽象类将是一个好习惯。如果没有,我会更喜欢使用接口。
一般来说,是的。使用必要的最少特定类型始终是一种好习惯。这也适用于具体的超类,而不仅仅是抽象类和接口。
public class MyClass{} // not an interface and not abstract
public class SubClass extends MyClass{}
public class OtherClass{
public MyClass getMyClass(){
return new SubClass();
}
]
在实践中,这取决于具体情况。如果一切都包含在一种方法的范围内,那真的没关系。
public void doStuff(){ // void method, so never going return any details
AbstractFoo foo1= new ConcreteFoo();
// no better than
ConcreteFoo foo2 = new ConcreteFoo();
// because nothing external to this method will ever know
}
然而,让开发人员总是使用最不具体的实现(或接口)的原因只是为了让它成为一种习惯。
答案取决于您的上下文。
例子:
// Abstract class template
abstract class AbstractFirst {
public void doSomething(){
this.doOne();
this.doSecond();
System.out.println("");
System.out.println("Test");
}
public abstract void doOne();
public abstract void doSecond();
}
// Concrete implementation
class ConcreteFirst extends AbstractFirst {
public void doOne(){System.out.print("One"); } // must be implemented
public void doSecond(){System.out.print("Second"); } // must be implemented
public static void main(String[] args){
ConcreteFirst cf = new ConcreteFirst();
c.doSomething();
}
}
这打印
OneSecond
Test
去安慰。这对于接口是不可能的。这种模式称为“模板方法模式”,是 GoF 模式之一
关于您的问题,没有这样的观点认为使用多态是一种不好的做法,在适用的地方使用它是一种很好的做法,但这取决于您将类的要求定义为纯虚拟又名接口的用例。
根据我的经验,抽象类总是包含某些接口的部分实现。例如,EJB 就是这种情况。它是一种更好的设计,可以将 API 及其实现分开,甚至是部分实现。所以我建议做一个接口和一个抽象类。但是对于引用使用接口而不是抽象类。