在展示范例之前,先介绍一些相关的概念和注意点,这是抽象类和接口的基础预备知识。
在继承的层次结构中,随着每个新子类的出现,类会变的越来越明确和具体。如果从一个子类追溯到父类,类就会变得更通用、更加不明确。类的设计应该确保父类包含子类的共同特征。
有时候,一个父类设计的非常抽象,以至于它没有任何具体的实例。这样的类称为抽象类。
抽象类中不实现,只声明的方法称为抽象方法。在方法头中用abstract修饰符表示。在类头使用abstract修饰符表示该类为抽象类。在UML类图中,抽象类和方法的名字用斜体表示。
抽象类和常规类很像,但是不能使用new操作符创建它的实例。抽象方法只有定义而没有实现。它的实现由子类提供。一个包含抽象方法的类必须声明为抽象类。
抽象类的构造方法定义为protected,因为它只被子类使用。创建一个具体子类的实例时,它的父类构造方法被调用以初始化父类中定义的数据域。
关于抽象类的几个注意点:
1)抽象方法不能包含在非抽象类中。如果抽象父类的子类不能实现所有的抽象方法,那么子类必须定义为抽象的。换句话说,在抽象类扩展的非抽象类中,必须实现所有的抽象方法。并且,抽象方法是非静态的。
2)包含抽象对象的类必须是抽象的。但是,可以定义一个不包含抽象方法的抽象类。在这种情况下,不能使用new操作符创建该类的实例。这种类是用来定义新子类的基类的。
3)即使子类的父类是具体的,这个子类也可以是抽象的。
4)子类可以覆盖父类的方法并将它定义为abstract。这是很少见的,但是它在当父类的方法实现在子类中变得不合法时是很有用的。在这种情况下,子类必须定义为abstract。
5)不能使用new操作符从一个抽象类创建一个实例,但是抽象类可以用作一种数据类型。
接口是一种与类相似的结构,只包含常量和抽象方法。它在很多方面都与抽象类很相似,但是它的目的是指明多个对象的共同行为。如,使用正确的接口,可以指明这些对象是可以比较的、可食用的或可克隆的。
Java中,接口被看作是一种特殊的类。就像常规类一样,每个接口都被编译为独立的字节码文件。与抽象类相似,不能使用new操作符创建接口的实例,但是大多数情况下,使用接口或多或少有点像使用抽象类。如可以使用接口作为引用变量的数据类型或类型转换的结果等等。
接口和抽象类的区别
或多或少可以使用和抽象类一样的方式使用接口,但是定义一个接口和定义一个抽象类有所不同,如下表所示:
接口可以扩展其他接口而不是类。一个类可以扩展它的父类同时实现多个接口 。
所有的类共享同一个根类Object,但是接口没有共同的根。与类类似,接口也可以定义一种类型。一个接口类型的变量可以引用任何实现该接口的类的实例。如果一个类实现了一个接口,那么这个接口就类似于该类的一个父类。可以将接口当作一种数据类型使用,将接口类型的变量转换成他的子类,反过来也可以。
运行效果如图:
实现的源代码如下所示:
package Blog;
public class blogTryProject {
public static void main(String[] args) {
TestChouXiang tcx = new TestChouXiang();
tcx.main(args);
}
}
//抽象类测试程序
class TestChouXiang{
public static void main(String[]args){
Rectangle rt = new Rectangle(4,5);
System.out.println(rt.toString());
System.out.println("Rectangle 的面积为:"+rt.getArea());
System.out.println("Rectangle 的周长为:"+rt.getPerimeter());
Circle c = new Circle(3);
System.out.println(c.toString());
System.out.println("Circle 的面积为:"+c.getArea());
System.out.println("Circle 的周长为:"+c.getPerimeter());
}
}
//抽象类GeometricObject
abstract class GeometricObject{
private String color = "White";
private boolean filled;
private java.util.Date dateCreated;
protected GeometricObject(){
dateCreated = new java.util.Date();
}
protected GeometricObject(String color,boolean filled){
dateCreated = new java.util.Date();
this.color = color;
this.filled = filled;
}
public String getColor(){
return col