接口_演练
接口引入
public abstract class Person {
private String name;
private int age;
public Person(String name, int age) {
this.name = name;
this.age = age;
}
public abstract void eat();
public abstract void sleep();
@Override
public String toString() {
return "姓名:" + name + ", 年龄:" + age;
}
}
用interface关键字声明接口
如果一个抽象类没有(实例)字段;
所有方法都是抽象方法
public abstract class Person {
public abstract void eat();
public abstract void sleep();
}
就可以把该抽象类改写为接口,接口可以理解为一种特殊的抽象类
在Java中用interface
关键字来声明接口。
public interface Person {
public abstract void eat();
public abstract void sleep();
}
因为接口定义的所有方法默认都是public abstract
的,所以这两个修饰符不需要写出来(写不写效果都一样)
public interface Person {
void eat();
void sleep();
}
implements关键字
一旦某个普通类继承了抽象类,就意味着必须要实现它定义的抽象方法
在接口的语境下,不再叫作继承,而叫做实现
一旦某个普通类实现了一个接口,即意味着它必须定义接口中的所有方法。我们把这个类叫作接口实现类。
要声明一个类实现某个接口,需要使用关键字implements
(不再是extends
!!!)
public class Student implements Person {
// 实现一个接口, 必须对接口中的所有方法提供定义,否则编译不通过!!!
}
简单说,就是需要实现接口中的所有方法(即:需对照着接口中的方法列表,在接口实现类中定义相应的方法!)
public class Student implements Person {
public void eat() {
}
public void sleep() {
// 需要把隐藏的public写出来
}
}
最终效果也是和抽象类一致的,也是定义了一种规范,凡是实现了xx接口就必须定义xx方法。例如上面Student类实现了Person接口就必须定义eat和sleep方法。
小结
接口可理解为一种特殊的抽象类
用interface
关键字声明接口,用implements
关键字实现接口
与抽象类类似,不能实例化,只能被继承实现,强迫实现类定义接口中的所有(抽象)方法,否则编译报错
实际也是定义了某种规范,凡是实现了xx接口就必须定义xx方法。
接口与抽象类
既然接口与抽象类如此相似,为什么Java语言的设计者还要大费周折地引入接口呢?
这是因为使用抽象类存在一个严重的问题,在Java中每个类只能继承一个类,也就是extends后面只能有一个类
但每个类却可以实现多个接口。
例如一个人往往有多重身份或者功能,例如一个人可以既是一个工人、也是一个爸爸。这样原有的继承机制就无法表达。
那为什么不干脆提供多重继承的机制?
这是因为Java语言设计者认为多重继承会让语言变得非常复杂,或者效率降低。
实际上,接口可以提供多重继承的大多数好处,还能避免多重继承的复杂性和低效性。
接口特性(试一试)
★不能创建接口对象,但可以声明接口变量
★接口变量只能引用实现了该接口的类的对象
与类的结构层次一样,也可以扩展接口
接口中不能有实例字段,但可以包含常量(可通过接口名访问)
★每个类只能有一个超类,但可以实现多个接口
练习
练习1
1定义一个接口Moveable
(可移动的),在接口中实现一个抽象方法:
void move();
2创建多个类实现接口:
- Car类在move()方法中,打印输出“汽车在公路上行驶”
- Ship类在move()方法中,打印输出“轮船在水面上航行”
- Aircraft类在move()方法中,打印输出“飞机在天空中飞行”
3编写主类,在main方法中:
创建3个Moveable类型的接口变量,分别引用Car、Ship、Aircraft类的对象。调用每个对象的move() 方法,观察输出结果
练习2
定义三个接口,分别表示具备吃的能力、喝的能力和睡的能力。
接口1:EatAbility
,包含一个方法 eat()
,表示吃的能力。
接口2:DrinkAbility
,包含一个方法 drink()
,表示喝的能力。
接口3:SleepAbility
,包含一个方法 sleep()
,表示睡的能力。
定义一个 Person
类,实现上述三个接口。
Person 类需要提供这三个方法的具体实现,方法内输出相应的提示信息,例如“人正在吃东西...”。
编写Test
类,在main方法中:
- 创建一个Person类对象。
- 使用3个接口类型的变量来引用该Person类对象。
- 调用接口变量对应的方法,验证Person类对象具备的3种能力。
练习3(★★★★★)
请创建一个Animal
动物类,要求有方法eat()
方法,方法输出一条语句“吃东西”。创建一个接口AnimalInfo
,接口里有一个抽象方法fly()
。创建一个Bird
类继承Animal类并实现接口AnimalInfo里的方法输出一条有语句“鸟儿飞翔”,重写父类的eat() 方法输出一条语句“鸟儿吃虫”。
创建Test类并添加main方法,在main方法中添加如下功能
(1)创建Animal类的对象并调用eat( )方法;
(2)使用父类引用Bird类的对象,并调用eat( )方法;
(3)使用接口引用Bird类的对象,并调用fly( )方法;
(4)使用Bird类引用Bird类的对象,调用eat( )方法和fly( )方法。
PS:父类=超类=基类
输出结果如下:
吃东西
鸟儿吃虫
鸟儿飞翔
鸟儿吃虫
鸟儿飞翔