Java面向对象之:多态性

1. 理解多态性:可以理解为一个事物的多种态性。
2.何为多态性:
       对象的多态性:父类的引用指向子类的对象(或子类的对象赋值给父类的引用)。
3. 多态的使用:虚拟方法调用
     有了对象多态性以后,我们在编译期,只能调用父类声明的方法,但在执行期实际执行的是子类重写父类的方法。简称:编译时,看左边;运行时,看右边。
     若编译时类型和运行时类型不一致,就出现了对象的多态性(Polymorphism).
  多态情况下,
       "看左边":看的是父类的引用(父类中不具备子类特有的方法〕
       "看右边":看的是子类的对象(实际运行的是子类重写父类的方法)。
4. 多态性的使用前提
    ①要有类的继承关系。
    ②要有方法的重写。
5. 对象的多态性:只适用于方法,不适用于属性(属性:编译和运行都看左边)。

来看以下几段代码:

1、Person类

public class Person {
	String naem;
	int age;
	int id=1001;
	public void eat() {
		System.out.println("人吃饭!");
	}
	public void walk() {
		System.out.println("人走路!");
	}
}

2、Woman类

public class Woman extends Person{
boolean isBeauty;
public void goShopping(){
System.out.println("女人喜欢购物!");
  }
public void eat(){
System.out.println("女人少吃,为了减肥。");
  }
public void walk(){
System.out.printin("女人,窈窕的走路! ");
  }
}

3、Man类

public class Man extends Person{
boolean isSmoking;
public void earnMoney(){
System.out.println("男人负责工作养家 !");
}
public void eat(){
System.out.println(" 男人多吃肉,长肌肉");
}
public void walk(){
System.out.println(" 男人霸气的走路");
}
}

4、Persontest类

public class Persontest {
	public static void main(String[] args) {
		Person p1= new Person();
		p1.eat();
		Man man = new Man();
		man.eat();
		man.age =25;
		man.earnMoney();			
		//***************
		
		//父类的引用指向子类的对象:多态性(对象的多态性!)
		Person p2=new Man();//多态性(对象的多态性!)
		Person p3=new Woman();
		System.out.println();
		//多态的使用:当调用子父类同名同参的方法时,实际调用的是子类中重写的方法-----虚拟方法调用
		p2.walk();//按ctrl点以下,跑到父类
		p2.eat();
		p3.walk();
		p3.eat();
//		p2.earnMoney();//不能调子类特有的方法!
		System.out.println(p2.id);//1001,父类中属性。
	}
}

多态性应用举例:

public class Animaltest {
	public static void main(String[] args) {
		Animaltest test =new Animaltest();
		test.fun(new Dog());
		test.fun(new Cat());
	}
	
	public void fun(Animal animal) {  //Animal animal=new Dog();
		animal.eat();
		animal.shout();
	}
	//如果没有多态性,就会写如下很多方法,去调用
	/*public void func(Dog dog) {
		dog.eat();
		dog.shout();
	}
	public void func(Cat  cat ) {
		cat.eat();
		cat.shout();
	}*/
}


class Animal{
	public void eat() {
		System.out.println("动物:吃饭!");
	}
	public void shout() {
		System.out.println("动物:叫!");
	}
}
class Dog extends Animal{
	@Override
	public void eat() {
		// TODO Auto-generated method stub
		System.out.println("狗,吃骨头!");
	}
	@Override
	public void shout() {
		// TODO Auto-generated method stub
		System.out.println("汪汪汪!");
	}
	
}
class Cat extends Animal{
	@Override
	public void eat() {
		// TODO Auto-generated method stub
		System.out.println("猫,吃🐟!");
	}
	@Override
	public void shout() {
		// TODO Auto-generated method stub
		System.out.println("喵喵喵!");
	}
	
}

虚拟方法的补充:

从编译和运行的角度看:
        重载,是指允许存在多个同名方法,而这些方法的参数不同。
        编译器根据方法不同的参数表,对同名方法的名称做修饰。
        对于编译器而言,这些同名方法就成了不同的方法。
它们的调用地址在编译期就绑定了。Java的重载是可以包括父类和子类的,即子类可以重载父类的同名不同参数的方法。所以:对于重载而言,在方法调用之前,编译器就已经确定了所要调用的方法,这称为“早绑定”或“静态绑定“;而对于多态,只有等到方法调用的那一刻,解释运行器才会确定所要调用的具体方法,这称为“晚绑定”或“动态绑定”。
引用一句 Bruce Eckel 的话:“不要犯傻,如果它不是晚绑定,它就不是多态。“

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值