目录
1. 定义与语法
2. 继承与实现
3. 成员变量
4. 访问修饰符
5. 设计目的
6. 应用场景
总结
在 Java 中,抽象类和接口是两种重要的抽象类型,用于定义规范和实现多态性,但它们在设计目的、语法结构和使用场景上有显著区别:
1. 定义与语法
抽象类 |
接口 |
使用abstract class 定义。 |
使用interface 定义。 |
可以包含抽象方法(无方法体)和具体方法(有方法体)。 |
JDK 8 之前只能包含抽象方法(默认public abstract ); JDK 8 + 可包含默认方法(default )、静态方法(static ); JDK 9 + 可包含私有方法(private )。 |
抽象方法必须用abstract 关键字声明。 |
抽象方法可以省略public abstract (默认添加)。 |
|
|
2. 继承与实现
抽象类 |
接口 |
一个类只能继承(extends )一个抽象类。 |
一个类可以实现(implements )多个接口。 |
子类必须实现抽象类中的所有抽象方法,否则子类也必须声明为抽象类。 |
实现类必须实现接口中的所有抽象方法(默认方法可选重写)。 |
抽象类可以继承其他类(包括普通类和抽象类),并实现多个接口。 |
接口可以继承(extends )多个其他接口,但不能继承类。 |
3. 成员变量
抽象类 |
接口 |
可以包含普通成员变量(实例变量和类变量)。 |
只能包含静态常量(默认public static final ),必须显式初始化。 |
示例: java<br>protected String name;<br>private int age;<br> |
示例: java<br>int MAX_SPEED = 100; // 默认public static final<br> |
4. 访问修饰符
抽象类 |
接口 |
抽象方法可以使用public 、protected (但不能是private )。 |
接口中的方法默认是public ,且不能使用其他访问修饰符(如protected )。 |
具体方法可以使用任意访问修饰符(public 、private 、protected 等)。 |
默认方法和静态方法默认是public ,私有方法只能在 JDK 9 + 中使用。 |
5. 设计目的
抽象类 |
接口 |
用于表示 **“是什么”**,是对一类事物的抽象(如Animal 类)。 |
用于表示 **“能做什么”**,是对行为的抽象(如Flyable 接口)。 |
提供公共的属性和行为,通过继承实现代码复用。 |
定义规范和契约,实现类必须遵循,支持多重实现(如一个类可同时实现Runnable 和Serializable )。 |
适用于需要共享状态或默认行为的场景(如抽象类中包含非抽象方法)。 |
适用于解耦和实现插件化架构(如微服务中的接口定义)。 |
6. 应用场景
- 抽象类:
- 当需要定义一组相关的类,且它们有共同的属性和行为时(如
Shape
抽象类包含getArea()
方法)。
- 当需要为子类提供默认实现(如模板方法模式)。
- 接口:
- 当需要定义一组不相关的类的共同行为时(如
Comparable
接口用于排序)。
- 当需要实现多重继承(通过实现多个接口)。
- 当设计需要遵循依赖倒置原则(高层模块依赖接口而非具体实现)。
总结
维度 |
抽象类 |
接口 |
关键字 |
abstract class |
interface |
继承 / 实现 |
单继承 |
多实现 |
方法类型 |
抽象方法和具体方法 |
抽象方法、默认方法、静态方法 |
成员变量 |
普通变量 |
静态常量 |
设计重点 |
代码复用和共同特征 |
行为规范和契约 |
访问修饰符 |
灵活(public 、protected 等) |
严格(默认public ) |
选择抽象类还是接口,取决于具体的设计需求:如果需要共享状态或默认行为,使用抽象类;如果需要定义行为规范且支持多重实现,使用接口。