java 多态

python 天生支持多态

一、概念

一个事物的多种形态,如即可以是工人也可以是学生

二、目的(作用)

调用一个事物(类)的方法或变量时,不用关心该类的具体形态是什么

三、语法

1、继承

父类名 对象名 = new 子类名();

2、接口

接口名 对象名 = new 接口类();

四、用法

1、成员变量

a、口诀

编译看左,运行看左

解释:编译的时候,看赋值符号左边的类中是否有这个变量名,若没编译出错;运行的时候,去赋值符号左边的类中取结果

b、例子

package cn.wt.day10;

public class Animal {
    int num = 10;
}
Animal.java
1 package cn.wt.day10;
2 
3 public class Dog extends Animal {
4     int num = 20;
5 }
Dog.java
1 package cn.wt.day10;
2 
3 public class Demon {
4     public static void main(String[] args) {
5         Animal dog = new Dog();
6         System.out.println(dog.num);    // 10 
7     }
8 }
Demon.java

2、成员方法

a、口诀

编译看左,运用看右

解释:编译时,看"="左边的类是否有这个方法名称;运行时,去"="右边的类找该方法并运行

b、例子

 1 package cn.wt.day10;
 2 
 3 public abstract class Animal {
 4     int num = 10;
 5 
 6     public abstract void eat();
 7 
 8     public void show(){
 9         System.out.println("我是一条狗");
10     }
11 }
Animal.java
 1 package cn.wt.day10;
 2 
 3 public class Dog extends Animal {
 4     int num = 20;
 5 
 6     @Override
 7     public void eat() {
 8         System.out.println("狗吃骨头");
 9     }
10 
11     public void watchHouse(){
12         System.out.println("狗看家");
13     }
14 }
Dog.java
 1 package cn.wt.day10;
 2 
 3 public class Demon {
 4     public static void main(String[] args) {
 5         Animal dog = new Dog();
 6         System.out.println(dog.num);    // 10
 7         // dog 无法使用 Dog()中的watchHouse(), 原因:编译不通过
 8         dog.eat();
 9         // show() 方法编译通过,在Dog类中找不到该方法,就向父类Animal中找
10         dog.show();
11     }
12 }
Demon.java

五、种类

1、向上转型

就是上面的例子,可以看成变量的隐式类型转换

2、向下转型(可以看成变量的显示转换)

a、出现原因

上面的例子中,使用多态后,对象无法调用子类中有而父类中没有的成员方法

b、语法

父类名 对象名A = new 子类名();
子类名 对象名B = (子类名) 对象名A;

c、例子

 1 package cn.wt.day10;
 2 
 3 public abstract class Animal {
 4     int num = 10;
 5 
 6     public abstract void eat();
 7 
 8     public void show(){
 9         System.out.println("我是动物");
10     }
11 }
Animal
 1 package cn.wt.day10;
 2 
 3 public class Dog extends Animal {
 4     int num = 20;
 5 
 6     @Override
 7     public void eat() {
 8         System.out.println("狗吃骨头");
 9     }
10 
11     public void watchHouse(){
12         System.out.println("狗看家");
13     }
14 }
Dog.java
 1 package cn.wt.day10;
 2 
 3 public class Demon {
 4     public static void main(String[] args) {
 5         Animal dog = new Dog();
 6         System.out.println(dog.num);    // 10
 7         // dog 无法使用 Dog()中的watchHouse(), 原因:编译不通过
 8         dog.eat();
 9         // show() 方法编译通过,在Dog类中找不到该方法,就向父类Animal中找
10         dog.show();
11         // 对象向下转型
12         Dog isDog = (Dog)dog;
13         isDog.watchHouse();
14     }
15 }
Demon.java

d、问题

数据类型的强制类型转换会出现溢出的现象,对象的向下转型也会出现类似这种情况

狗->动物->狗

 向上    向下

狗->动物->猫(错误),在不知道动物类型的情况下

六、instanceof

与pyhon中isinstance()函数用法相似

1、作用

解决上面的问题:不知道多态对象对应的子类是谁时,引起的错误

2、语法

对象 instanceof 类;

3、返回值类型

boolean

4、例子

 1 package cn.wt.day10;
 2 
 3 public abstract class Animal {
 4     int num = 10;
 5 
 6     public abstract void eat();
 7 
 8     public void show(){
 9         System.out.println("我是动物");
10     }
11 }
Animal.java
 1 package cn.wt.day10;
 2 
 3 public class Dog extends Animal {
 4     int num = 20;
 5 
 6     @Override
 7     public void eat() {
 8         System.out.println("狗吃骨头");
 9     }
10 
11     public void watchHouse(){
12         System.out.println("狗看家");
13     }
14 }
Dog.java
 1 package cn.wt.day10;
 2 
 3 public class Cat extends Animal {
 4     @Override
 5     public void eat() {
 6         System.out.println("猫吃鱼");
 7     }
 8 
 9     public void playMouse(){
10         System.out.println("猫玩老鼠");
11     }
12 }
Cat.java
 1 package cn.wt.day10;
 2 
 3 public class Demon {
 4     public static void main(String[] args) {
 5         Animal dog = new Dog();
 6         System.out.println(dog.num);    // 10
 7         // dog 无法使用 Dog()中的watchHouse(), 原因:编译不通过
 8         dog.eat();
 9         // show() 方法编译通过,在Dog类中找不到该方法,就向父类Animal中找
10         dog.show();
11 
12         System.out.println("=====================================");
13         //
14         showMessage(dog);
15         //
16         Animal cat = new Cat();
17         showMessage(cat);
18     }
19 
20     public static void showMessage(Animal animal){
21         if(animal instanceof Dog){
22             ((Dog) animal).watchHouse();
23         }else if (animal instanceof Cat){
24             ((Cat) animal).playMouse();
25         }
26     }
27 }
Demon.java

七、综合实例

1、电脑类  开启关闭电源、使用设备(符合)

2、USB接口  打开接口、关闭接口

3、鼠标类  实现接口、点击鼠标

4、键盘类  实现接口、写入文字

注意:向上转型可以自动完成,与变量的隐式转换相似

 1 package cn.wt.day10.demon;
 2 
 3 public class Computer {
 4     public void PowerOn(){
 5         System.out.println("打开电脑");
 6     }
 7 
 8     public void PowerOff(){
 9         System.out.println("关闭电源");
10     }
11 
12     public void useDevice(USB usb){
13         usb.open();
14         if(usb instanceof Mouse){
15             ((Mouse) usb).click();
16         }else if(usb instanceof KeyWord){
17             ((KeyWord) usb).type();
18         }
19         usb.close();
20     }
21 
22 }
Computer.java
1 package cn.wt.day10.demon;
2 
3 public interface USB {
4     public abstract void open();
5     public abstract void close();
6 }
USB.java
 1 package cn.wt.day10.demon;
 2 
 3 public class Mouse implements USB {
 4     @Override
 5     public void open() {
 6         System.out.println("打开鼠标连接");
 7     }
 8 
 9     @Override
10     public void close() {
11         System.out.println("关闭鼠标连接");
12     }
13 
14     public void click(){
15         System.out.println("点击鼠标");
16     }
17 }
Mouse.java
 1 package cn.wt.day10.demon;
 2 
 3 public class KeyWord implements USB {
 4     @Override
 5     public void open() {
 6         System.out.println("打开键盘连接");
 7     }
 8 
 9     @Override
10     public void close() {
11         System.out.println("关闭键盘连接");
12     }
13 
14     public void type(){
15         System.out.println("输入文字");
16     }
17 }
KeyWord.java
 1 package cn.wt.day10.demon;
 2 
 3 public class Demon {
 4     public static void main(String[] args) {
 5         Computer computer = new Computer();
 6         computer.PowerOn();
 7         // 鼠标
 8         USB useMouse = new Mouse();
 9         computer.useDevice(useMouse);
10         // 键盘, 使用匿名对象, 向上转型 自动转
11         computer.useDevice(new KeyWord());
12         computer.PowerOn();
13     }
14 }
Demon.java

 

posted @ 2020-01-23 22:10  市丸银  阅读(156)  评论(0编辑  收藏  举报