java学习笔记44-多态

允许不同类的对象对同一消息做出响应。即同一消息可以根据发送对象的不同而采用多种不同的行为方式。

    1)一个对象的实际类型是确定的
        例如: new Student(); new Person();等

    2)可以指向对象的引用的类型有很多
        例如: Student继承了Person类
        Student s1 = new Student();
        Person s2  = new Student();
        Object s3  = new Student();

        因为Person和Object都是Student的父类型

        注:一个对象的实际类型是确定,但是可以指向这个对象的引用的类型,却是可以是这对象实际类型的任意父类型。
        
    3)一个父类引用可以指向它的任何一个子类对象
        例如:
        Object o = new AnyClass();
        Person p = null;
        p = new Student();
        p = new Teacher();
        p = new Person();

    4)多态中的方法调用
        例如:
        public class Person{
            public void run(){}
        }
        public class Student extends Person{

        }
        //调用到的run方法,是Student从Person继承过来的run方法
        main:
            Person p = new Student();
            p.run();


        例如:
        public class Person{
            public void run(){}
        }
        public class Student extends Person{
            public void run(){
                //重写run方法
            }
        }
        //调用到的run方法,是Student中重写的run方法
        main:
            Person p = new Student();
            p.run();

        
        注:子类继承父类,调用a方法,如果a方法在子类中没有重写,那么就是调用的是子类继承父类的a方法,如果重写了,那么调用的就是重写之后的方法。
    

    5)子类中独有方法的调用
        例如:
        public class Person{
            public void run(){}
        }
        public class Student extends Person{
            public void test(){
            }
        }
        main:
            Person p = new Student();
            //调用到继承的run方法
            p.run();
            
            //编译报错,因为编译器检查变量p的类型是Person,但是在Person类中并没有发现test方法,所以编译报错.
            p.test();
        
        注:一个变量x,调用一个方法test,编译器是否能让其编译通过,主要是看声明变量x的类型中有没有定义test方法,如果有则编译通过,如果没有则编译报错.而不是看x所指向的对象中有没有test方法.

        思考:为什么编译器会是这样检查?

    6)子类引用和父类引用指向对象的区别
        Student s = new Student();
        Person p = new Student();
        
        变量s能调用的方法是Student中有的方法(包括继承过来的),变量p能调用的方法是Person中有的方法(包括继承过来的)。

        但是变量p是父类型的,p不仅可以指向Student对象,还可以指向Teacher类型对象等,但是变量s只能指向Studnet类型对象,及Student子类型对象。变量p能指向对象的范围是比变量s大的。
        

        Object类型的变量o,能指向所有对象,它的范围最大,但是使用变量o能调用到的方法也是最少的,只能调用到Object中的声明的方法,因为变量o声明的类型就是Object.


    
    7)多态的使用
        如果使用多态解决以下问题:
        public class Game{
            public void start(BasketBall ball){
                ball.run();
            }
        }
        
        public class BasketBall{
            public void run(){
                //执行篮球游戏程序
            }
        }

        在这种情况下,用户不断的变动需求:
        想要增加足球游戏的运行
        想要增加乒乓球游戏的运行
        想要增加橄榄球游戏的运行
        想要增加羽毛球球游戏的运行
        想要增加铅球游戏的运行
        ....

        如何处理?

猜你喜欢

转载自blog.csdn.net/onepiece_loves/article/details/88632667