接口和抽象类的异同
Posted ihan98
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了接口和抽象类的异同相关的知识,希望对你有一定的参考价值。
前言
这是2019年的第一篇博客,开始复习整理一下JavaSE的知识点(其实差不多是预习了,参照网上大佬的博客搬运了示例代码QAQ),写的比较简陋见笑了。。
正文
首先分别概括一下什么是接口和抽象类。
接口:简单说就是一系列抽象方法的集合,如果一个类实现(implements)了某个接口,即继承了这个接口的所有抽象方法,则该类必须实现这些抽象方法。
DEMO
//接口Externalizable
public interface Externalizable extends Serializable {
void writeExternal(ObjectOutput out) throws IOException;
void readExternal(ObjectInput in) throws IOException, ClassNotFoundException;
}
//实现Externalizable接口的Employee类
public class Employee implements Externalizable {
int employeeId;
String employeeName;
@Override
public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException {
employeeId = in.readInt();
employeeName = (String) in.readObject();
}
@Override
public void writeExternal(ObjectOutput out) throws IOException {
out.writeInt(employeeId);
out.writeObject(employeeName);
}
}
抽象类:首先,与接口不同的是,抽象类不能直接创建实例对象,抽象类中的抽象方法只能在其子类中实现(即通过extends的方式而不是implements),因此可以把抽象类看作是提供给继承的子类的一个模板。抽象类本身没有任何用处,它是为了继承而存在的,创建一个抽象类而不去继承它等于是做了无用功。
DEMO
//实现...接口的抽象类GenericServlet
public abstract class GenericServlet implements Servlet, ServletConfig, Serializable {
// abstract method
abstract void service(ServletRequest req, ServletResponse res);
void init() {
// Its implementation
}
// other method related to Servlet
}
//继承GenericServlet抽象类的HttpServlet子类
public class HttpServlet extends GenericServlet {
void service(ServletRequest req, ServletResponse res) {
// implementation
}
protected void doGet(HttpServletRequest req, HttpServletResponse resp) {
// Implementation
}
protected void doPost(HttpServletRequest req, HttpServletResponse resp) {
// Implementation
}
// some other methods related to HttpServlet
}
两者对比
参数 | 接口 | 抽象类 |
---|---|---|
构造方法 | 不能有 | 可以有 |
方法 | 只能有抽象方法 | 可以包含普通方法 |
继承 | 一个类可实现多个接口 | 只能继承一个抽象类 |
成员变量 | 只能是public static final类型 | 可以是各种类型 |
接口和抽象类分别适用于何种场合?这里搬运网上某大佬博客里的一个例子。
门和警报的例子:门都有open( )和close( )两个动作,此时我们可以定义通过抽象类和接口来定义这个抽象概念:
//抽象类
abstract class Door {
public abstract void open();
public abstract void close();
}
//接口
interface Door {
public abstract void open();
public abstract void close();
}
现在需要部分门具有报警alarm( )的功能,该如何实现?
- 将三个功能都放在抽象类中,但是有的门并不具备报警的功能 ×
- 将三个功能都放在接口中,有些类需要实现报警的功能但是并不具备open和close的功能(如火灾报警器)×
- 从1和2中可以看出,open和close是门的固有属性,而alarm则是特殊的附加属性,因此最好的解决办法是单独将报警设计为一个接口,包含alarm()行为,Door设计为单独的一个抽象类,包含open和close两种行为。再设计一个报警门继承Door类和实现Alarm接口。√
interface Alram {
void alarm();
}
abstract class Door {
void open();
void close();
}
class AlarmDoor extends Door implements Alarm {
void oepn() {
//....
}
void close() {
//....
}
void alarm() {
//....
}
}
参考:
http://www.importnew.com/12399.html
https://www.cnblogs.com/dolphin0520/p/3811437.html
以上是关于接口和抽象类的异同的主要内容,如果未能解决你的问题,请参考以下文章