一、抽象类
被abstract修饰的类,称为抽象类。被abstract修饰的方法,称为抽象方法。
- 类具有的成分,抽象类都具有。可以包含成员变量、方法(普通方法和抽象方法都可以)、构造器、初始化块、内部类。
- 抽象类和抽象方法都必须使用abstract修饰,抽象方法不能有方法体。
- 抽象方法虽然具有构造器,但是不能用来创建对象,构造器提供给子类创建对象时调用父类构造器使用。
- 含有抽象方法的类(包括直接定义了一个抽象方法;或继承了一个抽象父类,但没有完全实现父类包含的所有抽象方法;或实现了一个接口,但没有完全实现接口包含的所有抽象方法)只能定义成抽象类。
抽象类体现的是一种模板模式的设计,抽象类作为多个子类的同用模板,子类在抽象类的基础上进行拓展、改造,但子类总体会大致保留抽象类的行为方式。
抽象类中的抽象方法需要子类重写,子类重写时不加static修饰
;如果加 static 修饰,那么子类也需要定义成抽象类。
抽象类是否由构造器?是否可以创建对象?
- 抽象类本身意味着抽象,抽象不能具体化。
- 抽象类作为类,一定具有构造器,而且必须由构造器,提供给子类创建对象时调用父类构造器使用。
- 假如抽象类可以创建对象,那么当实例对象调用抽象方法时,没有方法体,方法执行不了,所以抽象类不能创建对象。
二、接口
-
接口就是一种规范,定义了某一批类所需要遵守的规范。
-
接口使规范和实现分离。
-
接口是更加彻底的抽象,没有构造器。
-
接口的修饰符只能是 public 和 default。
-
接口只能继承(extends)一个或多个接口,不能继承类。
-
接口中可以包含成员变量(只能是静态常量)、方法(只能是抽象实例方法、类方法、默认方法)、内部类(包括内部接口、枚举)。
在 JDK1.8 之前,接口中只能拥有:
- 抽象方法(
public abstract
) - 常量(
public static final
)
在 JDK1.8 之后,增加了三种方法:
- 默认方法(必须加 default):只能用接口的 实现类来调用。
- 静态方法(static):只能用 接口名称来调用,不能用接口实现类来调用。如果实现了多个接口,多个接口中的同名静态方法并不会冲突,因为静态方法只能通过接口名称来调用。
- 私有方法(private): JDK1.9 才支持。通常是提供给其他私有方法或默认方法调用。
特别注意:
- 如果实现了多个接口,多个接口中的
同名静态方法并不会冲突
,因为静态方法只能通过接口名称来调用。 - 当一个类,继承了一个父类,有实现了多个接口。父类中的成员方法域接口中的默认方法重名,该类会
就近执行父类的成员方法
。 - 当一个类实现了多个接口,且接口中存在同名的默认方法时,两默认方法冲突,所以实现类
必须重写这个同名默认方法
。
三、接口与抽象类的异同
普通类:具体实现。
抽象类:具体实现、规范。
接口:规范。