接口:
概述:就是一种公共规范标准
特点:
- 接口是一种引用数据类型
- 接口中只能定义常量和方法(抽象方法,默认方法,静态方法,私有方法)
- 接口中不能定义成员变量和构造方法,也没有静态代码块
- 接口不能创建对象,只能通过其实现类(子类)来实
定义接口:
public interface 接口名{
常量
抽象方法
默认方法
静态方法
私有方法
}
实现接口:
- 创建一个类
- 实现该接口
public class 类名 implements 接口名{
}
接口中的成员:
jadk1.7及其以前只能写:
常量
- 默认修饰符:public static final
- 接口中的常量可以供接口直接使用
- 接口中的常量可以供子类和子类对象直接使用
抽象方法:没有方法体的方法
接口中的抽象方法的默认修饰符:public abstract
- public abstract 返回值类型 方法名(参数类型 参数,…);
- public 返回值类型 方法名(参数类型 参数,…);
- abstract 返回值类型 方法名(参数类型 参数,…);
- 返回值类型 方法名(参数类型 参数,…);
- 如果实现类(子类)是普通类,就必须实现接口中的所有抽象方法
- 如果实现类(子类)是抽象类,就可以不实现接口中的抽象方法
jdk1.8额外添加了:
默认方法:需要加Default
格式:
- public default 返回值类型 方法名(参数列表){
方法体
}- 接口中的默认方法可以供子类对象调用
- 接口中的默认方法可以供子类重写,但是重写的时候不需要加 default
静态方法
- public static 返回值类型 方法名(参数列表){
方法体
}- 静态方法只能供接口直接使用,实现(子类)类不能使用
jdk1.9额外添加了:
私有的方法
- private 返回值类型 方法名(参数列表){
}
私有非静态方法只能供接口中的默认方法使用,私有方法非静态方法使用
私有方法只能在接口中直接使用
私有静态方法
- private static 返回值类型 方法名(参数列表){
}
私有静态只能供接口中的默认方法、私有方法、静态方法使用
接口和类之间的关系:实现关系
- 单实现:一个类实现一个接口
- 多实现:一个类实现多个接口
格式:
- public class 类名implements 接口1,接口2,~{
}
-
多个实现接口中没有重名的抽象方法,实现(子类)类需要全部实现所有抽象方法
-
多个接口中有重名的抽象方法,实现(子类)类只需要实现一个抽象方法
-
多个接口中没有重名的默认方法,实现(子类)类就正常使用,不需要重写默认方法
-
多个接口中有重名的默认方法,实现(子类)类必须重写重名的默认方法,并且要去掉default关键字
-
静态方法只能供接口直接使用,跟实现(子类)类无关,正常使用
-
私有方法只能供接口的默认方法、私有方法、静态方法使用,跟实现(子类)类也无关,正常使用
子接口重写父接口的默认方法,必须加default关键字;
实现类重写父接口的默认方法,必须去掉default关键字;
接口和接口之间的关系:继承关系
- 单继承:一个接口继承一个接口
- 多继承:一个接口同时继承多个接口
- 多层继承:一个接口继承另一个接口,而另一个接口又继承另一个接口
注意:
- 如果多个父接口中有同名的抽象方法,那么实现类只需要实现一次即可
- 如果多个父接口中有同名的默认方法,那么子接口必须重写默认方法,必须要加default关键字
单继承:
public interface 接口A extends 接口B{
}
接口A:子接口
接口B:父接口
多继承:
public interface 接口A extends 接口B,接口C,~{
}
接口A:子接口
接口B\C…:父接口
多层继承:
在单继承或多继承接口继续继承
类可以继承一个类也可以实现一个接口
当一个类,即继承一个父类,又实现若干个接口时
格式:
public class 类名 extends 父类 implements 接口A,接口B,~{
}
注意:
- 如果接口和父类中有同名的默认方法,优先调用父类的默认方法
- 如果接口和父类中有同名的抽象方法,那么子类必须重写一次抽象方法
注意:
- 接口也是一种引用数据类型
- 接口编译之后也会有.class文件
- 接口中不能有构造方法,只能通过其实现(子类)来创建
普通类:成员变量,构造方法,成员方法,静态代码块
抽象类:成员变量,构造方法,成员方法,静态代码块,抽象方法 -->不能直接创建对象
接口:常量,默认方法,静态方法,私有方法,抽象方法 -->不能直接创建对象
一个类只能继承一个父类,但是一个类可以实现多个接口
一般父类使用抽象类,一般一个类需要扩展功能就实现接口
多态
多态指的是:同一种行为,对于不同的事物具有不同的表现形式。这就叫做多态
程序中的多态:指同一个方法,对于不同的对象具有不同的方法体称为多态
多态的条件:
- 要有继承、实现
- 要有方法的重写(为了让多态有意义)
- 要有父类的引用指向子类的对象(接口的引用指向实现类的对象)
格式:
父类名 变量名=new 子类名(实参);
多态中的成员访问特点:
- 成员变量:
- 编译看左边,运行看左边
- 成员方法:
- 非静态方法:编译看左边,运行看右边
- 静态方法:编译看左边,运行看左边
只有非静态方法是编译看左边,运行看右边,其它的都是编译看左边,运行看左边
多态的好处和使用:
- 好处:
- 实际开发的过程中,父类类型作为方法形式参数
- 传递子类对象给方法,进行方法的调用,更能体现出多态的扩展性与便利
- (使用父类(接口)作为方法的参数,用来接收所有子类(实现类)对象)
向上转型
- 向上转型:多态本身是子类类型向父类类型向上转换的过程,这个过程是自动转换的,类似基本数据类型的自动转换
也就是说,当父类引用指向一个子类对象时,便是向上转型
使用格式:
父类类型 变量名=new 子类类型();
如:Aimal a=new Cat();//向上转型 自动完成
向下转型
- 向下转型:父类类型向子类类型向下转换的过程,这个过程是强制的
一个已经向上转型的子类对象,将父类引用转为子类引用,可以使用强制类型转换的格式,便是向下转型
使用格式:
子类类型 变量名=(子类类型)父类变量名;
如:Aimal a=new Cat();
Cat c=(Cat) a;
自动类型转换:把范围小的类型 自动转换为 范围大的类型
强制类型转换:把范围大的类型 强制转换为 范围小的类型 范围小的数据类型 变量名=(范围小的数据类型)范围大的数据类型
为什么要转换
当使用多态方式调用方法时,首先检查父类中是否有该方法,如果没有,则编译错误
也就是说,不能调用子类拥有,而父类没有的方法。编译都错误,更别说运行了
这也是多态给我们带来的一点“小麻烦”。所以,想要调用子类特有的方法,必须做向下转型
翻译:其实就是父类的引用不能调用子类独有的方法
类型转换异常:ClassCastException
instansof关键字:
- 父类对象名 instanceof 数据类型
- 判断前面的对象是否属于后面的数据类型
- 如果变量属于该数据类型,返回trun
- 如果变量不属于该数据类型,返回false
接口多态:
- 实现类实现接口
- 方法的重写
- 接口类型的引用指向实现类的对象