一.接口
1.接口的定义和使用
接口名:和类名一样,首字母大写
public interface 接口名{
//接口中的成员,一般写一些抽象方法
}
public class 类名 implements 接口名{
//复写接口中所有的抽象方法
}
2.接口的成员热点:
(1)JDK7以及以前的版本
1)接口中可以定义变量,默认被 public static final 修饰 (也就是常量)
2)接口中只能是抽象方法,不能有其他方法。
(2)JDK8之后
3)允许在接口定义默认方法(用于接口升级,它的实现类不用重写),使用public default 修饰,是带方法体的方法。
4)允许在接口中定义静态方法,使用只能用接口名调用(其实现类的对象无法调用)
public class DemoSM {
public static void main(String[] args) {
SMImpl sm = new SMImpl();
//sm.show();
StaticMethod.show();
}
}
//定义实现类
class SMImpl implements StaticMethod {
//如果两个实现两个接口,有相同的静态方法,无逻辑冲突问题
//因为其静态方法只能用接口名调用
}
interface StaticMethod {
public static void show(){
System.out.println("我是SM中的静态方法");
}
}
(3)JDK9
5)允许在接口中定义私有方法(用于抽取默认方法相同的部分),用private修饰,只能用于本类,外类不能访问。
3.接口与类之间的关系
1)类与类的关系:单继承的关系
2)类与接口的关系:多实现的关系
3)接口与接口:多继承的关系
二.多态
1.理解:同一个对象有多种表现形态(数据类型,可以是父类类型,也可以是本类类型)
举例: Animal a = new Dog();
a = new Cat();
Dog d = new Dog();
2.多态的前提
(1)必须要有继承/实现的关系
(2)要有方法复写
(3)有父类引用变量指向子类(或实现类)对象
ps:在参数传递时,也可以体现多态的特性
3.多态的好处:【在定义一个方法时,把方法的参数写成父类类型,调用方法时可以传递任意的子类对象】
public class Demo {
public static void main(String[] args) {
//传入一个子类对象,用父类变量接收再使用父类方法调用
animalEat(new Cat());
animalEat(new Dog());
}
//好处,把方法的参数写成父类|接口类型,调用方法时,可以传递任意的子类对象
public static void animalEat(Animal a){
//Animal a =new Cat()
//a =new Dog();
a.eat();
//传入一个用动物变量接收的狗类型对象
if(a instanceof Cat){
Cat cat = (Cat)a;
cat.catchMouse();
}
if(a instanceof Dog){
//强转简化方法
((Dog)a).lookDoor();
}
}
}
abstract class Animal {
public abstract void eat();
}
class Cat extends Animal{
@Override
public void eat(){System.out.println("猫吃鱼");}
//猫的特有方法
public void catchMouse(){System.out.println("猫抓老鼠");}
}
class Dog extends Animal{
@Override
public void eat() {System.out.println("狗吃骨头");}
//狗的特有方法
public void lookDoor(){System.out.println("狗看门");}
}
打印结果:
猫吃鱼
猫抓老鼠
狗吃骨头
狗看门
4.多态的弊端【不能直接调用子类的特有方法,除非向下转型(强制转换)】
(1)向上转型:其实就是多态的写法
如:Animal a = new Dog();
(2)向下转型:把父类类型转换为子类类型
如:Dog d = (Animal)a ;
(3)注意事项,向下转型可能出现类型转换异常(ClassCastExcetpion)
所以我们我们如果想让父类对应的转换达到预期,可以在转换之前加个判断
//instanceof可以用来判断对象是否可满足某个特定类型
if(a instanceof Dog){
//强转简化方法
((Dog)a).lookDoor();
}