1.概述
接口就是规范,就是协议,定下的一组规则.体现了现实世界中"如果你是...则必须能..."的思想.继承是"is a"的关系(如Student is a Person),而接口是"has a"的关系.
例如 : 电脑都预留了可以插入的USB设备的接口,USB接口具备基本的数据传输开启和关闭功能.你能否用USB进行连接或具备通信功能,就看你是否遵循了USB接口的规范.
接口的本质是契约,规范,标准,就像我们的法律一样.制定好了以后要遵守.
2.格式
interface Developer { //抽象方法,只有方法名,没有方法体.但方法的功能是已知的,只是没有提供具体的实现. //public abstract void run(); //可以简写为 void run(); 接口内可以定义全局常量. public static final int i =10; //可以简写为 int i =10; } class Ielts implements Developer { //重写接口的抽象方法 @Override void run() { System.out.println("雅迪小电瓶跑的快"); } }
例子 : Jante类对Developer类来说,叫做子类.
Jante类对Vehicle接口来说,叫做实现类.
public class Developer1 { public static void main(String[] args) { new Vehicle() { //创建了匿名实现类的匿名对象 @Override public void run() { System.out.println("捷安特增加动力的方式是充电"); } }.run(); //执行的是实现类的run方法 } } //接口 interface Vehicle { //public abstract void run(); void run(); } class Jante extends Developer implements Vehicle { @Override public void run() { System.out.println("捷安特增加动力的方式是充电"); } } 控制台 : 捷安特增加动力的方式是充电
3.特点
- 类可以实现多个接口.
- 如果类implements多个接口,则需实现该些接口的所有抽象方法,否则将该类声明为抽象类.
- 类针对于多个接口的实现,一定程度上弥补的类只有单继承的局限.
- (复习) 类与类之间只能单继承.
- 而类与接口之间可以多实现.
- 接口与接口之间可以多继承.
4.接口的多态性
public void takingVehicle(Vehicle Vehicle) { System.out.println("已经调用了run方法"); Vehicle.run(); } Jante j = new Jante(); takingVehicle(j); //即Vehicle Vehicle = new Jante(); 虽然接口不能创建对象 但接口的引用可以指向了实现类的对象 同样遵循编译在左, 运行在右 编译时调用接口的抽象方法, 运行时调用实现类重写接口的方法 此处也体现多态无处不在
5.区分抽象类与接口
区别点 抽象类 接口 定义 可以包含抽象方法的类 主要是抽象方法和全局常量的集合 组成 构造器,抽象方法,普通方法,常量,变量 全局常量,抽象方法,(jdk8.0:默认方法,静态方法) 使用 子类继承抽象类(extends) 子类实现接口(implements) 关系 抽象类可以实现多个接口 接口不允许继承抽象类,但允许继承多个接口 常见设计模式 模板方法 简单工厂方法,工厂方法,代理模式 对象 都不能通过直接new产生对象,都是通过对象的多态性产生实例化对象 局限 抽象类有单继承的缺陷 接口没有此局限 实际 作为一个模板 作为一种标准,一种协议 选择 如果抽象类和接口都可以实现的话,优先使用接口,避免单继承的局限性
6.JDK8.0添加的特性(了解)
(1). 接口内可以声明静态方法 : 如
public static void eat(){ //可以有方法体; } 该静态方法可以由"接口名.eat()"调用,但不可以由"实现类的对象名.eat()"调用. (2). 接口中可以声明默认方法 : 如 default关键字不可省略. public default void sleep(){ //可以有方法体. }
接口中声明的默认方法可以被实现类继承,实现类在没有重写该方法的情况下,默认调用接口中的默认方法,如果实现类重写了该默认方法,则调用的是自己重写的方法.
(3). 接口冲突 :
如果类实现了两个接口,两个接口中定义了同名同参数的默认方法.如果实现类的对象调用该默认方法,将会报错,二者同优先级,编译器不知道该调用哪个接口的默认方法.如果实现类又重写了该默认方法,则调用的是实现类重写的方法.
(4). 类优先原则 :
子类继承了父类并实现了接口,接口和父类中声明了同名同参数列表的方法(接口中声明的是默认方法),默认情况下,子类未重写该方法,则子类调用的是父类的方法.
(5). 如何在子类中调用父类或接口被重写的方法?
super.Xxx() 调用父类被重写的方法.
接口名.super.Xxx() 调用接口中被重写的方法
7.JDK添加的特性(了解)
(1). 接口中可以声明私有方法 :
private void Xxx(){ //方法体 }
8.补充 :
(1)问题 : 为什么接口中声明的属性是全局的(public),静态的(static),不可变的(final)?
答 :
- 声明为public类型,表明他们可以在任何地方被访问.
- 声明为static,表明他们属于接口,表明不管多少类实现了该接口,都只有这一份属性.
- 声明为final,表明他们的值在初始化后不可改变,有助于保证数据的安全性.