В чем разница между динамическим и статическим полиморфизмом в Java?


может ли кто-нибудь привести простой пример, который объясняет разницу между динамический и Static полиморфизм в Java?

12 83

12 ответов:

полиморфизм

1. Статическое связывание/связывание во время компиляции/раннее связывание / перегрузка метода.(в том же классе)

2. Динамическая привязка/привязка во время выполнения/поздняя привязка / переопределение метода.(в разных классах)

перегрузка пример:

class Calculation {  
  void sum(int a,int b){System.out.println(a+b);}  
  void sum(int a,int b,int c){System.out.println(a+b+c);}  

  public static void main(String args[]) {  
    Calculation obj=new Calculation();  
    obj.sum(10,10,10);  // 30
    obj.sum(20,20);     //40 
  }  
}  

переопределение пример:

class Animal {    
   public void move(){
      System.out.println("Animals can move");
   }
}

class Dog extends Animal {

   public void move() {
      System.out.println("Dogs can walk and run");
   }
}

public class TestDog {

   public static void main(String args[]) {
      Animal a = new Animal(); // Animal reference and object
      Animal b = new Dog(); // Animal reference but Dog object

      a.move();//output: Animals can move

      b.move();//output:Dogs can walk and run
   }
}
  • перегрузка метода была бы примером статического полиморфизма

  • в то время как переопределение было бы примером динамического полиморфизма.

    потому что, в случае перегрузки, во время компиляции компилятор знает, какой метод связать с вызовом. Однако он определяется во время выполнения для динамического полиморфизма

динамический (во время выполнения) полиморфизм полиморфизм существовал во время выполнения. Здесь компилятор Java не понимает, какой метод вызывается во время компиляции. Только JVM решает, какой метод вызывается во время выполнения. Перегрузка метода и переопределение метода с использованием методов экземпляра являются примерами динамического полиморфизма.

например,

  • рассмотрим приложение, которое сериализует и десериализует разных типы документов.

  • мы можем иметь "документ" как базовый класс и другой тип документа классы, вытекающие из него. Например, XMLDocument, WordDocument и т. д.

  • класс документа определит 'Serialize ()' и ' De-serialize() ’ методы как виртуальные и каждый производный класс будет реализовывать эти методы по-своему основаны на фактическом содержании документов.

  • когда различные типы документов должны быть сериализации/де-сериализации объектов документ будет передан ссылка на класс’ Document ' (или указатель) и когда ‘ Serialize () ’ или ‘ De-serialize () ’ метод вызываются на нем, соответствующие версии виртуальных методов.

статический (время компиляции) полиморфизм - это полиморфизм, проявляющийся во время компиляции. Здесь компилятор Java знает, какой метод вызывается. Перегрузка метода и переопределение метода с использованием статических методов; переопределение метода с использованием частных или конечных методов являются примерами статического полиморфизма

например,

  • объект employee может иметь два метода print (), один из которых не принимает Аргументы и один, принимающий строку префикса, которая будет отображаться вместе с данные сотрудников.

  • учитывая эти интерфейсы, когда метод print() вызывается без каких-либо аргументы, компилятор, глядя на аргументы функции знает, какая функция предназначен для вызова и генерирует объектный код соответственно.

для получения более подробной информации, пожалуйста, прочитайте "что такое полиморфизм" (Google it).

полиморфизм: Полиморфизм-способность объекта принимать различные формы. Наиболее распространенное использование полиморфизма в ООП происходит, когда ссылка на родительский класс используется для ссылки на объект дочернего класса.

Динамическое Связывание / Полиморфизм Времени Выполнения:

полиморфизм времени выполнения, также известный как переопределение метода. В этом механизме, с помощью которого вызов переопределенной функции решается при a время выполнения.

public class DynamicBindingTest {

    public static void main(String args[]) {
        Vehicle vehicle = new Car(); //here Type is vehicle but object will be Car
        vehicle.start();       //Car's start called because start() is overridden method
    }
}

class Vehicle {

    public void start() {
        System.out.println("Inside start method of Vehicle");
    }
}

class Car extends Vehicle {

    @Override
    public void start() {
        System.out.println("Inside start method of Car");
    }
}

выход:

внутренний метод запуска автомобиля

статическое связывание / время компиляции полиморфизм:

какой метод должен быть вызван, решается только во время компиляции.

public class StaticBindingTest {

    public static void main(String args[])  {
       Collection c = new HashSet();
       StaticBindingTest et = new StaticBindingTest();
       et.sort(c);

    }

    //overloaded method takes Collection argument
    public Collection sort(Collection c){
        System.out.println("Inside Collection sort method");
        return c;
    }


   //another overloaded method which takes HashSet argument which is sub class
    public Collection sort(HashSet hs){
        System.out.println("Inside HashSet sort method");
        return hs;
    }

}

выход: Внутри коллекции сортировка metho

способ перегрузки пример compile time/static polymorphism потому что привязка метода между вызовом метода и определением метода происходит во время компиляции и зависит от ссылки на класс(ссылка создается во время компиляции и переходит в стек).

способ переопределения пример run time/dynamic polymorphism потому что привязка метода между вызовом метода и определением метода происходит во время выполнения и зависит от объекта класса (созданный объект во время выполнения и идет в кучу).

простыми словами :

статический полиморфизм : то же имя метода перегружен С другим типом или количеством параметров в тот же класс (разные подписи). Целевой вызов метода разрешается во время компиляции.

динамический полиморфизм: тот же метод переопределяется С та же подпись в разные классы. Тип объекта, на котором вызывается метод, не известен во время компиляции, но будет определен во время выполнения.

вообще перегрузка не будет рассматриваться как полиморфизм.

из Java tutorial страница:

подклассы класса могут определять свое собственное уникальное поведение и при этом совместно использовать некоторые из тех же функций родительского класса

привязка относится к связи между вызовом метода и определением метода.

Это изображение ясно показывает, что такое привязка.

binding

на этом рисунке, " a1.methodOne () "вызов привязывается к соответствующему определению methodOne () и" a1.вызов methodTwo () " привязывается к соответствующему определению methodTwo ().

для каждого вызова метода должно быть правильное определение метода. Это правило в java. Если компилятор не видит правильного определения метода для каждого вызова метода, он выдает ошибку.

теперь перейдем к статической привязке и динамической привязке в java.

Статическая Привязка В Java:

статическая привязка-это привязка, которая происходит во время компиляции. Это также называется ранняя привязка, потому что привязка происходит до программы на самом деле работает

.

статическая привязка может быть продемонстрирована как в ниже изображение.

enter image description here

на этом рисунке ‘a1 'является ссылочной переменной типа класса A, указывающей на объект класса A. ‘a2' также является ссылочной переменной типа класса A, но указывает на объект класса B.

во время компиляции, при привязке, компилятор не проверяет тип объекта, на который указывает конкретная ссылочная переменная. Он просто проверяет тип ссылочной переменной, через которую вызывается метод и проверяет существует ли определение метода для него в этом типе.

например, для "a1.метод ()" вызов метода на приведенном выше рисунке компилятор проверяет, существует ли определение метода для метода() в классе A. потому что 'a1' является типом класса A. Аналогично, для "А2.метод ()" вызов метода, он проверяет, существует ли определение метода для метода () в классе A. потому что 'a2' также является типом класса A. Он не проверяет, на какой объект указывают ‘a1’ и ‘a2’. Этот тип привязки называется статическая привязка.

Динамическая Привязка В Java:

динамическая привязка-это привязка, которая происходит во время выполнения. Также называется поздней привязкой, потому что привязка происходит, когда программа на самом деле бегущий.

во время выполнения фактические объекты используются для привязки. Например, для "a1.вызов метода ()" на приведенном выше рисунке будет вызван метод() фактического объекта, на который указывает ‘a1’. Для "А2.метод ()" вызов, метод () фактический объект, на который указывает ‘a2’, будет вызван. Этот тип привязки называется динамической привязкой.

динамическая привязка приведенного выше примера может быть продемонстрирована, как показано ниже.

enter image description here

ссылка статические привязки и динамического связывания в языке Java

Статический Полиморфизм: где решение решить, какой метод выполнить, определяется во время компиляции. Примером этого может быть перегрузка метода.

Динамический Полиморфизм: где решение выбрать, какой метод выполнить, устанавливается во время выполнения. Примером этого может быть переопределение метода.

Способ Перегрузки называется Статический Полиморфизм и Полиморфизм Времени Компиляции или Статическое Связывание потому что перегруженные вызовы метода разрешаются во время компиляции компилятором на основе списка аргументов и ссылки, по которой мы вызываем метод.

и Способ Переопределения называется Динамический Полиморфизм или просто полиморфизм или Runtime Method Dispatch или Динамическое Связывание потому что переопределенный вызов метода разрешен во время выполнения.

для того чтобы понять, почему это так, давайте возьмем пример Mammal и Human класс

class Mammal {
    public void speak() { System.out.println("ohlllalalalalalaoaoaoa"); }
}

class Human extends Mammal {

    @Override
    public void speak() { System.out.println("Hello"); }

    public void speak(String language) {
        if (language.equals("Hindi")) System.out.println("Namaste");
        else System.out.println("Hello");
    }

}

Я включил выход, а также байт-код в ниже строки кода

Mammal anyMammal = new Mammal();
anyMammal.speak();  // Output - ohlllalalalalalaoaoaoa
// 10: invokevirtual #4 // Method org/programming/mitra/exercises/OverridingInternalExample$Mammal.speak:()V

Mammal humanMammal = new Human();
humanMammal.speak(); // Output - Hello
// 23: invokevirtual #4 // Method org/programming/mitra/exercises/OverridingInternalExample$Mammal.speak:()V

Human human = new Human();
human.speak(); // Output - Hello
// 36: invokevirtual #7 // Method org/programming/mitra/exercises/OverridingInternalExample$Human.speak:()V

human.speak("Hindi"); // Output - Namaste
// 42: invokevirtual #9 // Method org/programming/mitra/exercises/OverridingInternalExample$Human.speak:(Ljava/lang/String;)V

и, глядя на приведенный выше код, мы можем видеть, что байт-коды humanMammal.говори (), человек.говорят () и человек.говорят ("хинди") являются совершенно разные, потому что компилятор может различать их на основе списка аргументов и ссылки на класс. И вот почему Способ Перегрузки называется Статический Полиморфизм.

но байт-код для anyMammal.говорят () и humanMammal.speak () - это то же самое, потому что в соответствии с компилятором оба метода вызываются по ссылке Mammal, но вывод для обоих вызовов методов отличается, потому что во время выполнения JVM знает, какой объект содержит ссылка и JVM вызывает метод на объекте, и именно поэтому переопределение метода известно как динамический полиморфизм.

таким образом, из приведенного выше кода и байт-кода ясно, что на этапе компиляции метод вызова рассматривается из ссылочного типа. Но во время выполнения метод будет вызван из объекта, который держит ссылка.

если вы хотите знать больше об этом вы можете прочитать больше о как JVM обрабатывает перегрузку и переопределение метода Внутренне.

полиморфизм времени компиляции (статическое связывание / раннее связывание): в статическом полиморфизме, если мы вызываем метод в нашем коде, то какое определение этого метода должно быть вызвано на самом деле разрешается только во время компиляции.

(или)

во время компиляции Java знает, какой метод вызывать, проверяя сигнатуры метода. Таким образом, это называется полиморфизмом времени компиляции или статическим связыванием.

Динамический Полиморфизм(Позднее Связывание / Время Выполнения Полиморфизм): во время выполнения Java ожидает, пока среда выполнения не определит, на какой объект фактически указывает ссылка. Разрешение метода было принято во время выполнения, из-за чего мы называем полиморфизм времени выполнения.

перегрузка метода-это полиморфизм времени компиляции, давайте возьмем пример, чтобы понять концепцию.

class Person                                            //person.java file
{
    public static void main ( String[] args )
    {
      Eat e = new Eat();
       e.eat(noodle);                                //line 6
    }

   void eat (Noodles n)      //Noodles is a object    line 8                     
   {

   }
   void eat ( Pizza p)           //Pizza is a object
  {

  }

}

в этом примере у человека есть метод eat, который представляет, что он может есть пиццу или лапшу. Что метод eat перегружен, когда мы компилируем этого человека.java компилятор разрешает вызов метода " e. eat (noodles) [который находится в строке 6] с определением метода, указанным в строке 8, то есть это метод, который принимает noodles как параметр и весь процесс выполняется компилятором, поэтому это полиморфизм времени компиляции. Процесс замены вызова метода определением метода называется связыванием, в этом случае он выполняется компилятором, поэтому он называется ранним связыванием.

полиморфизм относится к способности объекта вести себя по-разному для одного и того же триггера.

статический полиморфизм (полиморфизм времени компиляции)

  • статический полиморфизм решает, какой метод выполнять во время компиляции время.
  • перегрузка метода является примером статического полиморфизма, и это requred к случается статический полиморфизм.
  • статический полиморфизм достигается за счет статического связывания.
  • статический Полиморфизм происходит в том же классе.
  • назначение объекта не требуется для статического полиморфизма.
  • наследование не участвует для статического полиморфизма.

Динамический Полиморфизм (Runtime Polymorphism)

  • динамический полиморфизм решает, какой метод выполнять во время выполнения.
  • переопределение метода является примером динамического полиморфизма, и это requred для происходит динамически полиморфизм.
  • динамический полиморфизм достигается за счет динамического связывания.
  • динамический полиморфизм происходит между различными классами.
  • требуется, когда объект подкласса назначается суперклассу объект для динамического полиморфизма.
  • наследование, связанное с динамическим полиморфизмом.