java-多态

多态:

同一个(事物)对象在不同时刻表现出的不同的状态。

例:

  狗是狗,狗是动物
  水是(液态,固态,气态)

多肽的前提:
  1-要有继承关系
  2-要有方法重写(来体现不同状态)
      如果不写方法重写,就失去了多肽的意义
      动物 dw = new 狗();
          dw.show();//狗表现的状态
      动物 dw = new 猫();
          dw.show();//猫表现的状态
  3-要有父类引用指向子类


    父类 f = new 子类() ;
     左边        右边

多态中的成员访问特点:
    父类 f = new 子类() ;
      左边        右边

   1-成员变量 :
     编译看左边,运行看左边(变量不存在覆盖)
   2-构造方法:创建子类对象时候,访问父类的构造方法,对父类数据进行初始化。
   3-成员方法:
      编译看左边,编译看右边。(方法存在覆盖)
   4-静态方法:
     编译看左边,运行看左边(静态只能被静态重写,静态和类相关)

注意:由于只有成员方法存在方法重写,所以它运行看右边。
案例:
package day09;


public class Fu {
    public int num=100;
    
    public void show(){
    	System.out.println("父类方法");
    }
}
package day09;


public class Zi extends Fu {
   public int num=333;
   public int num2=444;
   
   public void show(){
	   System.out.println("子类方法");
   }
   
   public void method(){
	   System.out.println("子类独有方法!");
   }
}
package day09;


public class ZiFuMain {


	/**
	 * @param args
	 */
	public static void main(String[] args) {
		//创建指向子类的父类引用
		Fu f = new Zi();
		
		System.out.println(f.num);//输出父类的num,编译看左边,运行看左边
		
		//System.out.println(f.num2);//报错,编译看左边,左边父类中没有num2变量
		
		f.show();//编译看左边,左边父类show方法被子类重写,顾运行看右边
		//f.method();//报错,编译看左边父类没有method()方法,所以报错。


	}


}

输出:

100
子类方法

多态的好处:
1-提高了代码的维护性
2-提高了代码的扩展性
下面来演示一个显示多态扩展性的案例
cat类:

package day09;


public class Cat extends Animal {
      public void eat(){
    	  System.out.println("猫吃老鼠");
      }
      public void sleep(){
    	  System.out.println("猫打着呼噜睡觉");
      }


}
dog类:
package day09;


public class Dog extends Animal{
	public void eat(){
		System.out.println("狗吃骨头");
	}
	public void sleep(){
		System.out.println("狗趴着睡觉");
	}


}
pig类:
package day09;


public class Pig extends Animal {
	public void eat(){
		System.out.println("猪吃饲料");
	}
	public void sleep(){
		System.out.println("猪侧着睡觉");
	}


}
测试类1:
package day09;


public class MianDemo {


	/**
	 * @param args
	 */
	public static void main(String[] args) {
		Cat c = new Cat();
		c.eat();
		c.sleep();
		// 创建Dog对象
		Dog d = new Dog();
		d.eat();
		d.sleep();
		// 创建Pig对象
		Pig p = new Pig();
		p.eat();
		p.sleep();
	}


}
输出:
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉

 思考:假如有很多类呢......
 引入 工具类AnimalTool,由于测试类里面的操作就是创建对象和调用操作,顾新建一个工具类存放功能方法
 那么以上代码就可以改为
package day09;


public class AnimalTool {
	private AnimalTool(){}//设置为私有,防止外界创建对象
     public static void useCat(Cat c){
    	 c.eat();
    	 c.sleep();
     }
     public static void useDog(Dog d){
    	 d.eat();
    	 d.sleep();
     }
     public static void usePig(Pig p){
    	 p.eat();
    	 p.sleep();
     }
}
测试类2:
package day09;


public class MainDemo2 {


	/**
	 * @param args
	 */
	public static void main(String[] args) {
		System.out.println("***************方法直接调用版本*****************");
		// 创建Cat对象
		Cat c = new Cat();
		c.eat();
		c.sleep();
		// 创建Dog对象
		Dog d = new Dog();
		d.eat();
		d.sleep();
		// 创建Pig对象
		Pig p = new Pig();
		p.eat();
		p.sleep();

		System.out.println("***************借助工具类调用*****************");
		AnimalTool.useCat(c);
		AnimalTool.useDog(d);
		AnimalTool.usePig(p);


	}


}

输出:
***************方法直接调用版本*****************
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉
***************借助工具类调用*****************
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉


重点:思考工具类,加入我还想创建老虎,狮子,长颈鹿,企鹅....等等等动物呢,程序显得很臃肿,万一不小心把以上代码改动,还会造成程序错误。
     有什么好的解决方法么???
     答:使用父类创建子类引用方式。
     则工具类代码将更改为(最后//代码改进**************以下的部分)

package day09;

public class AnimalTool {
	private AnimalTool(){}//设置为私有,防止外界创建对象
     public static void useCat(Cat c){
    	 c.eat();
    	 c.sleep();
     }
     public static void useDog(Dog d){
    	 d.eat();
    	 d.sleep();
     }
     public static void usePig(Pig p){
    	 p.eat();
    	 p.sleep();
     }
     //代码改进**************
     public static void useAnimal(Animal a){
    	 a.eat();
    	 a.sleep();
     }
}

三种调用方法最终测试类:

package day09;


public class AnimalMain {


	/**
	 * 
	 */
	public static void main(String[] args) {
		System.out.println("***************方法直接调用版本*****************");
		// 创建Cat对象
		Cat c = new Cat();
		c.eat();
		c.sleep();
		// 创建Dog对象
		Dog d = new Dog();
		d.eat();
		d.sleep();
		// 创建Pig对象
		Pig p = new Pig();
		p.eat();
		p.sleep();


		// 思考:假如有很多类呢......
		// 引入工具类AnimalTool,由于测试类里面的操作就是创建对象和调用操作,顾新建一个工具类存放功能方法
		// 那么以上代码就可以改为
		System.out.println("***************借助工具类调用*****************");
		AnimalTool.useCat(c);
		AnimalTool.useDog(d);
		AnimalTool.usePig(p);
		
		//根据工具类里面的父类指向子类的引用,代码又可以进一步改进为一下调用方式(推荐使用)
		System.out.println("***************借助工具类改进版调用*****************");
		AnimalTool.useAnimal(c);
		AnimalTool.useAnimal(d);
		AnimalTool.useAnimal(p);


	}


}
***************方法直接调用版本*****************
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉
***************借助工具类调用*****************
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉
***************借助工具类改进版调用*****************
猫吃老鼠
猫打着呼噜睡觉
狗吃骨头
狗趴着睡觉
猪吃饲料
猪侧着睡觉

  • 4
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值