Java 多态性



Java 多态性

Java中的运行时多态性

运行时多态性
动态方法分派是一个过程,其中调用了覆盖的方法在运行时解决,而不是在编译时解决。
在此过程中,将通过超类的引用变量调用重写的方法。确定要调用的方法是基于参考变量所引用的对象。
让我们先了解运行时多态性之前的向上转换。

向上转换

如果父类的引用变量引用子类的对象,称为向上转换。例如:

Java 多态性_https://bianchenghao6.com_【Java 基础教程】_第1张

 class A{
}
class B extends A{
}

 A a=new B();
//upcasting

对于上播,我们可以使用类类型或接口类型的引用变量。例如:
 interface I{
}
class A{
}
class B extends A implements I{
}

在这里,B类的关系为:
 B IS-A AB IS-A IB IS-A Object

由于对象是Java中所有类的根类,因此我们可以编写B IS-A对象。


Java运行时多态性示例

在此示例中,我们将创建两个类Bike和辉煌。 Splendor类扩展了Bike类并覆盖其run()方法。我们通过Parent类的引用变量来调用run方法。因为它引用了子类对象,并且子类方法覆盖了Parent类方法,所以在运行时将调用子类方法。
由于方法调用是由JVM而不是编译器确定的,因此称为运行时多态。
 class Bike{
    void run(){
        System.out.println("running");
    }
}
class Splendor extends Bike{
    void run(){
        System.out.println("running safely with 60km");
    }
    public static void main(String args[]){
        Bike b = new Splendor();
        //upcasting b.run();
    }
}

输出:
 running safely with 60km.

Java运行时多态示例: Bank

考虑一个场景,其中Bank是一个提供获取利率的方法的类。但是,利率可能因银行而异。例如,SBI,ICICI和AXIS银行提供的利率为8.4%,7.3%和9.7%。

Java 多态性_https://bianchenghao6.com_【Java 基础教程】_第2张

注意: 方法覆盖中也给出了此示例,但没有向上转换。

 class Bank{
    float getRateOfInterest(){
        return 0;
    }
}
class SBI extends Bank{
    float getRateOfInterest(){
        return 8.4f;
    }
}
class ICICI extends Bank{
    float getRateOfInterest(){
        return 7.3f;
    }
}
class AXIS extends Bank{
    float getRateOfInterest(){
        return 9.7f;
    }
}
class TestPolymorphism{
    public static void main(String args[]){
        Bank b;
        b=new SBI();
        System.out.println("SBI Rate of Interest: "+b.getRateOfInterest());
        b=new ICICI();
        System.out.println("ICICI Rate of Interest: "+b.getRateOfInterest());
        b=new AXIS();
        System.out.println("AXIS Rate of Interest: "+b.getRateOfInterest());
    }
}

输出:
 SBI Rate of Interest: 8.4ICICI Rate of Interest: 7.3AXIS Rate of Interest: 9.7

Java运行时多态示例: Shape

 class Shape{
    void draw(){
        System.out.println("drawing...");
    }
}
class Rectangle extends Shape{
    void draw(){
        System.out.println("drawing rectangle...");
    }
}
class Circle extends Shape{
    void draw(){
        System.out.println("drawing circle...");
    }
}
class Triangle extends Shape{
    void draw(){
        System.out.println("drawing triangle...");
    }
}
class TestPolymorphism2{
    public static void main(String args[]){
        Shape s;
        s=new Rectangle();
        s.draw();
        s=new Circle();
        s.draw();
        s=new Triangle();
        s.draw();
    }
}

输出:
 drawing rectangle...drawing circle...drawing triangle...

Java运行时多态性示例: Animal

 class Animal{
    void eat(){
        System.out.println("eating...");
    }
}
class Dog extends Animal{
    void eat(){
        System.out.println("eating bread...");
    }
}
class Cat extends Animal{
    void eat(){
        System.out.println("eating rat...");
    }
}
class Lion extends Animal{
    void eat(){
        System.out.println("eating meat...");
    }
}
class TestPolymorphism3{
    public static void main(String[] args){
        Animal a;
        a=new Dog();
        a.eat();
        a=new Cat();
        a.eat();
        a=new Lion();
        a.eat();
    }
}

输出:
 eating bread...eating rat...eating meat...

具有数据成员的Java运行时多态性

方法(而不是数据成员)被覆盖,因此运行时多态性不能由数据成员实现。
在下面给出的示例中,两个类都有一个数据成员速度限制。我们正在通过父类的引用变量访问数据成员,该引用变量引用了子类对象。由于我们正在访问未被覆盖的数据成员,因此它将始终访问Parent类的数据成员。

注意: 规则: 数据成员无法实现运行时多态。

 class Bike{
    int speedlimit=90;
}
class Honda3 extends Bike{
    int speedlimit=150;
    public static void main(String args[]){
        Bike obj=new Honda3();
        System.out.println(obj.speedlimit);
    //90 }
}

输出:
 90

具有多级继承的Java运行时多态性

让我们看一下具有多级继承的运行时多态性的简单示例。
 class Animal{
    void eat(){
        System.out.println("eating");
    }
}
class Dog extends Animal{
    void eat(){
        System.out.println("eating fruits");
    }
}
class BabyDog extends Dog{
    void eat(){
        System.out.println("drinking milk");
    }
    public static void main(String args[]){
        Animal a1,a2,a3;
        a1=new Animal();
        a2=new Dog();
        a3=new BabyDog();
        a1.eat();
        a2.eat();
        a3.eat();
    }
}

输出:
 eatingeating fruitsdrinking Milk


尝试输出

 class Animal{
    void eat(){
        System.out.println("animal is eating...");
    }
}
class Dog extends Animal{
    void eat(){
        System.out.println("dog is eating...");
    }
}
class BabyDog1 extends Dog{
    public static void main(String args[]){
        Animal a=new BabyDog1();
        a.eat();
    }
}

输出:
 Dog is eating

因为,BabyDog没有覆盖eat()方法,所以调用了Dog类的eat()方法。