Java多态

Java多态

  1. 多态基础

Java 多态,多态是面向对象特征之一,它允许我们以不同的方式执行单个动作。例如,假设我们有一个Animal类,它有一个方法sound()。由于这是一个泛型类,所以我们不能给它一个实现,如:汪汪喵喵等。我们不得不给出一个通用的消息。

public class Animal{
   ...
   public void sound(){
      System.out.println("动物有各种各样的声音");
   }
}

现在假设我们动物类的两个子类:DogCat扩展Animal类。我们可以提供相同的方法实现

public class Dog extends Animal{
...
    @Override
    public void sound(){
        System.out.println("汪汪");
    }
}
public class Cat extends Animal{
...
    @Override
    public void sound(){
        System.out.println("喵喵");
    }
}

尽管我们对所有子类sound()都有共同的操作,但是有不同的方法来执行相同的操作。这是多态的完美示例(允许我们以不同方式执行单个操作的功能)。仅调用泛型sound()方法没有任何意义,因为每个Animal都有不同的声音

  1. 运行时多态和编译时多态

    1. java 中有两种类型的多态:

      • 静态多态又称编译时多态

      • 动态多态又称运行时多态

运行时多态(静态多态)

在编译器时间内解析的多态称为静态多态。方法重载是编译时多态的一个例子。

方法重载:如果方法的参数在参数的数量,顺序和数据类型上不同,这允许我们有多个具有相同名称的方法。

  1. 静态多态的例子

    方法重载是Java支持静态多态的方式之一。这里有两个相同的方法add()的定义,其中add()方法的使用将在编译时由参数列表决定。

    class Calculator
    {
        int output(int a)
        {
            return a;
        }
        int add(int a, int b)
        {
             return a+b;
        }
        int  multiplication(int a, int b)  
        {
             return a*b;
        }
    }
    public class Demo
    {
       public static void main(String args[])
       {
           Calculator obj = new Calculator();
           System.out.println(obj.output(10));
           System.out.println(obj.add(10,20));
           System.out.println(obj.multiplication(10,20));
       }
    }
    

    输出

    10
    30
    300
    
  2. 运行时多态(动态多态)

    它也称为动态方法调度。动态多态是一个在运行时解析对重写方法的调用的过程。

    例:

    有两个类ABCXYZABC是父类,XYZ是子类。子类覆盖父类的myMethod()方法。将子类对象分配给父类引用,因此为了确定将调用哪个方法,将在运行时确定对象的类型。对象的类型决定了要调用哪个版本的方法(而不是引用的类型)。

    class ABC{
       public void myMethod(){
        System.out.println("方法一");
       }
    }
    public class XYZ extends ABC{
    
       public void myMethod(){
        System.out.println("方法二");
       }
       public static void main(String args[]){
        ABC obj = new XYZ();
        obj.myMethod();
       }
    }
    

    输出:

    方法二
    

    几个通俗易懂的例子:

    ABC obj = new ABC();
    obj.myMethod();
    // 调用ABC的myMethod
    
    XYZ obj = new XYZ();
    obj.myMethod();
    // 调用XYZ的myMethod
    
    ABC obj = new XYZ();
    obj.myMethod();
    // 调用XYZ的myMethod
    

Java的静态和动态绑定

  1. 静态绑定

    编译器在编译时可以解析的绑定称为静态或早期绑定。staticprivatefinal方法的绑定是编译时。 因为是无法覆盖这些方法,并且在编译时确定类的类型。

    1. 静态绑定示例

      有两个类,人类和男孩。这两个类都有相同的方法walk(),但方法是静态的,这意味着它不能被覆盖,所以即使我在创建对象obj时使用了Boy类的对象,它也会调用父类方法。因为引用是Human类型(父类)。因此,每当静态,私有和最终方法的绑定发生时,类的类型由编译器在编译时确定,然后绑定发生在那里。

      class Human{
         public static void walk()
         {
             System.out.println("Human walks");
         }
      }
      class Boy extends Human{
         public static void walk(){
             System.out.println("Boy walks");
         }
         public static void main( String args[]) {
             Human obj = new Boy();
             Human obj2 = new Human();
             obj.walk();
             obj2.walk();
         }
      }
      

      输出:

      Human walks
      Human walks
      
    2. 动态绑定

      当编译器无法在编译时解析调用/绑定时,此类绑定称为动态绑定或后期绑定。方法覆盖是动态绑定的一个完美示例,因为覆盖父类和子类具有相同的方法,在这种情况下,对象的类型确定要执行的方法。对象的类型在运行时确定,因此称为动态绑定

      动态绑定示例

      class Human{
         //Overridden Method
         public void walk()
         {
             System.out.println("Human walks");
         }
      }
      class Demo extends Human{
         //Overriding Method
         public void walk(){
             System.out.println("Boy walks");
         }
         public static void main( String args[]) {
             Human obj = new Demo();
             Human obj2 = new Human();
             obj.walk();
             obj2.walk();
         }
      }
      

      输出:

      Boy walks
      Human walks
      
    3. 静态绑定与动态绑定的差异

      1. 静态绑定在编译时发生,而动态绑定在运行时发生。
      2. 私有,静态和最终方法的绑定总是在编译时发生,因为这些方法无法被覆盖。当实际发生方法覆盖并将父类型的引用分配给子类类型的对象时,则在运行时期间解析此类绑定。
      3. 重载方法的绑定是静态的,并且覆盖方法的绑定是动态的
posted @   叶晨烁  阅读(69)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· C#/.NET/.NET Core优秀项目和框架2025年2月简报
· Manus爆火,是硬核还是营销?
· 一文读懂知识蒸馏
· 终于写完轮子一部分:tcp代理 了,记录一下
点击右上角即可分享
微信分享提示