一、多态性是什么?
子类的对象赋给父类的引用
可以理解为一个事物的多种形态。
public class PersonTest {
public static void main(String[] args) {
Person p1 = new Person();
p1.age = 34;
p1.name = "熊";
Man man = new Man();
man.age=12;
man.name = "QUQU";
man.eat();
//********************************************************
//对象的多态性:父类的引用指向子类的对象
Person p2 = new Man();//可以new person的子类
//多态的使用:当调用子父类同名同参数的方法时,实际执行的是子类重写父类的方法----虚拟方法调用
p2.eat();
}
}
二、多态的使用
1.虚拟方法调用
有了对象的多态性以后,我们在编译期,只能调用父类中声明的方法,但在运行期,我们实际执行的是子类重写父类的方法。
总结:编译,看左边;运行,看右边。
public class AnimalTest {
public static void main(String[] args) {
AnimalTest test = new AnimalTest();
test.func(new Dog());
test.func(new Cat());
}
public void func(Animal animal) {
animal.eat();
animal.shout();
}
}
//父类
class Animal{
public void eat() {
System.out.println("动物:进食");
}
public void shout(){
System.out.println("动物:叫");
}
}
//子类1
class Dog extends Animal{
public void eat() {
System.out.println("狗吃狗粮");
}
public void shout() {
System.out.println("狗会大声叫!");
}
}
//子类2
class Cat extends Animal{
public void eat() {
System.out.println("猫吃鱼");
}
public void shout() {
System.out.println("猫会喵喵喵!");
}
}
2.多态性的使用前提
- 类的继承关系
- 方法的重写
3.多态性的限制
只适用于方法,不适用于属性
总结:方法的重载与重写
从编译和运行的角度看:
重载,是指允许存在多个同名方法,而这些方法的参数不同。编译器根据方法不同的参数表,对同名方法的名称做修饰。对于编译器而言,这些同名方法就成了不同的方法。他们的调用地址在编译期就绑定了。Java的重载是可以包括父类和子类的,即子类可以重载父类的同名不同参数的方法。
所以:对于重载而言,在方法调用之前,编译器就已经确定了所要调用的方法,这称为"早绑定"或"静态绑定";
而对于多态,只有等到方法调用的那一刻,解释运行器才会确定所要调用的具体方法,这称为"晚绑定"或"动态绑定"。
引用一句Bruce Eckel的话:"不要犯傻,如果它不是晚绑定,它就不是多态。"