目录
概述
一方面,有时必须从几个类中派生出一个子类,继承他们所有的属性和方法。但是Java不支持多继承。有了接口,就可以得到多重继承的效果。
另一方面,有时必须从几个类中抽取一些共同的行为特征,而它们之间又没有is-a的关系,仅仅是具有相同的行为特征而已。例如:鼠标、打印机、键盘、充电器、手机等都支持USB连接。
接口就是规范,定义了一组规则,体现了现实世界中“如果你是/要.....则必须得....”的思想。而继承是一个“是不是”的关系,接口实现的是“能不能”的关系。
接口的本质是规范、标准,就像法律一样,制定之后都要遵守。
接口的使用
-
接口使用interface来定义。
-
Java中,接口和类是并列的两个结构。
-
如何定义接口:定义接口中的成员
-
全局常量:public static final
-
抽象方法:public abstract
-
静态方法:public static
-
接口中定义的静态方法,只能通过接口直接调用,并执行方法体,而实现类无法调用。
-
-
默认方法:default
-
通过实现类的对象,可以调用接口中的默认方法。
-
实现类可以重写默认方法。
-
如果子类(实现类),继承的父类和实现的接口中声明了同名同参数的方法,且子类没有重写此方法的情况下,默认调用的是父类的方法。(类优先原则)
-
如果实现类实现了多个接口,而多个接口中存在同名同参的默认方法,且实现类没有重写此方法的情况下,会报错。(接口冲突)要求必须重写。
-
调用父类的方法:super.method()
-
调用接口的默认方法:接口名.super.method()
-
-
-
-
接口不能定义构造器,意味着不能实例化。
-
接口通过让类去实现(implements)的方式使用。
-
如果实现类覆盖了接口中所有的抽象方法,则此类可以实例化;
-
否则实现类仍为一个抽象类。
-
-
类可以实现多接口,接口可以继承多接口。
public class InterfaceTest {
public static void main(String[] args) {
System.out.println(Flyablle.MAX_SPEED);
System.out.println(Flyablle.MIN_SPEED);
// Flyablle.MIN_SPEED = 2;
Bullet b = new Bullet();
b.fly();
}
}
interface Flyablle {
// 全局常量,自动省略public static final
public static final int MAX_SPEED = 7900;
int MIN_SPEED = 1;
// 抽象方法,自动省略public abstract
public abstract void fly();
void stop();
}
interface attackable {
public abstract void attack();
}
class Bullet extends Object implements Flyablle, attackable {
@Override
public void attack() {
System.out.println("子弹可以攻击人");
}
@Override
public void fly() {
System.out.println("子弹通过火药爆炸飞行");
}
@Override
public void stop() {
System.out.println("子弹打中物体停止");
}
}
具体实例
-
接口的具体使用,体现多态性。
-
接口,实际上就是定义了一种规范。
public class USBTest {
public static void main(String[] args) {
Computer computer = new Computer();
// 1.创建接口的非匿名实现类的非匿名对象
Flash flash = new Flash();
computer.trancsferData(flash);
// 2.创建接口的非匿名实现类的匿名对象
computer.trancsferData(new Printer());
// 3.创建接口的匿名实现类的非匿名对象
USB phone = new USB() {
@Override
public void start() {
System.out.println("手机开启工作");
}
@Override
public void stop() {
System.out.println("手机结束工作");
}
};
computer.trancsferData(phone);
// 4.创建接口的匿名实现类的匿名对象
computer.trancsferData(new USB() {
@Override
public void start() {
System.out.println("MP4开启工作");
}
@Override
public void stop() {
System.out.println("MP4结束工作");
}
});
}
}
class Computer {
public void trancsferData(USB usb) {// 声明的是USB,传的是具体实现类
// USB usb = new Flash();
// 体现接口的多态性
usb.start();
System.out.println("开始传输数据");
usb.stop();
}
}
interface USB {
void start();
void stop();
}
class Flash implements USB {
@Override
public void start() {
System.out.println("U盘开启工作");
}
@Override
public void stop() {
System.out.println("U盘停止工作");
}
}
class Printer implements USB {
@Override
public void start() {
System.out.println("打印机开启工作");
}
@Override
public void stop() {
System.out.println("打印机停止工作");
}
}
面试题:抽象类与接口有哪些异同?
- 相同点
- 抽象类和接口都不能实例化。
- 都可以包含抽象方法。
- 不同点
抽象类abstract | 接口interface | |
---|---|---|
实现方式 | 被子类继承 | 被类实现 |
与子类/实现类关系 | 子类只能继承1个抽象类 | 类可以实现多个接口 |
构造器 | 有构造器,供子类调用 | 没有 |
变量 | 普通变量 | 只能是公共静态常量 public static final |
方法的实现 | 可以声明、实现方法 | 可以声明方法,不能实现(Java7) (Java8之后可以有静态方法、默认方法) |
方法的类型 | 可以有非抽象方法 | 只能有抽象方法(Java7) (Java8之后可以有静态方法、默认方法) |
思想 | 抽象类别,A is a B | 抽象功能,A 实现 B |