Java面向对象特征之三:多态
多态性是指允许不同类型的对象对同一消息做出相应。具有灵活性、抽象、行为共享、代码共享的优势,共享就意味着最大化利用和简洁,还有就是加载速度。
一、多态的作用
消除类型之间的耦合关系。即同一事件发生在不同的对象上会产生不同的结果。
二、多态的理解
1.多态是同一个行为具有多个不同表现形式或形态的能力。
2.多态就是同一个接口,使用不同的实例而执行不同操作。
3.多态性是对象多种表现形式的体现。
三、多态存在的三个前提
1.要有继承关系
2.子类要重写父类的方法
3.父类引用指向子类对象
四、多态的实现形式有两种:
1)编译时多态性(重载方法)
对于多个同名方法,如果在编译时能够确定执行同名方法中的哪一个,则称为编译时多态性.
2)运行时多态性(重写方法)
在编译时不能确定,只能在运行时才能确定执行多个同名方法中的哪一个,则称为运行时多态性
五、多态中成员的特点
1.多态成员变量:编译运行看左边
Fu f=new Zi();
System.out.println(f.num); //f是Fu中的值,只能取到父中的值
2.多态成员方法:编译看左边,运行看右边
Fu f1=new Zi();
//f1的门面类型是Fu,但实际类型是Zi,所以调用的是子类重写后的方法。
System.out.println(f1.show());
六、instanceof关键字
作用:用来判断某个对象是否属于某种数据类型。
注意: 返回类型为布尔类型
使用案例:
Fu f1=new Zi();
Fu f2=new Son();
if(f1 instanceof Zi){
System.out.println("f1是Zi的类型");
}
else{
System.out.println("f1是Son的类型");
}
七、多态的转型
多态的转型分为 向上转型 和 向下转型 两种
向上转型:多态本身就是向上转型过的过程
使用格式:父类类型 变量名 = new 子类类型();
适用场景:当不需要面对子类类型时,通过提高扩展性,或者使用父类的功能就能
完成相应的操作。
向下转型:一个已经向上转型的子类对象可以使用强制类型转换的格式,将父类引用
类型转为子类引用各类型
使用格式:子类类型 变量名 =(子类类型) 父类类型的变量;
适用场景:当要使用子类特有功能时。
八、多态的好处
1.可替换性
2.可扩展性
3.接口性(多态是超类通过方法签名,向子类提供了一个共同的接口)
4.简洁性
5.灵活性
代码示例:
//父类——Animal
public class Animal {
int num = 44;
static int age = 2;
public void eat() {
System.out.println("动物都需要吃东西");
}
public static void sleep() {
System.out.println("动物需要睡觉");
}
public void run() {
System.out.println("长腿的动物爱奔跑");
}
}
//子类——Dog
public class Dog extends Animal {
int num = 5;
static int age = 5;
String name = "Tom";
public void eat() {
System.out.println("我爱吃狗粮");
}
public static void sleep() {
System.out.println("我是一只爱睡觉的狗狗");
}
public void catchMouse() {
System.out.println("我喜欢捉耗子");
}
}
//测试类
public class Demo_Test {
public static void main(String[] args) {
Animal a = new Dog();
a.eat();
a.sleep();
a.run();
System.out.println(a.num);
System.out.println(a.age);
}
}
结果
从上面的打印结果我们可以得出:
1)成员变量:打印父类,子类没有出来;
2)成员方法:父类为静态的就打印父类(这里静态的调用不规范,正确形式用类名
调用),非静态的直接打印子类的;
// 当调用父类里没有的方法时会报错
a.catchMouse();
此时,多态不能使用自己特有的属性和方法,这是多态的弊端。
解决方法:把这个父类引用指向子类对象a(强制类型转换),再强制变回Dog类型。
这样a就是Dog类型的引用了,指向的也是Dog对象了。
//测试类
public class Demo_Test {
public static void main(String[] args) {
Animal a = new Dog();
a.eat();
a.sleep();
a.run();
System.out.println(a.num);
System.out.println(a.age);
System.out.println("------------------");
Dog d = (Dog) a;
d.eat();
Dog.sleep; // 静态用类名调用
d.run();
d.catchMouse();
}
}
结果: