Polymorphisme vs Héritage

Supposons que j’ai deux classes: Animal et Dog. Le chien est une sous-classe d’Animal. Je fais le code suivant:

Animal a = new Dog(); 

Maintenant, je peux appeler des méthodes de la classe Dog à travers la variable a.

Mais ma question est la suivante: si je peux appeler toutes les méthodes d’Animal à travers les objects Dog (inheritance), pourquoi utiliser le principe du polymorphism? Je peux simplement déclarer:

 Dog d = new Dog(); 

Avec cette déclaration peut utiliser toutes les méthodes de Animal et les méthodes de chien. Alors, pourquoi utiliser le polymorphism? Merci beaucoup pour votre réponse.

En Java, les concepts de polymorphism et d’inheritance sont “soudés”; en général, cela ne doit pas nécessairement être ainsi:

  • Le polymorphism vous permet d’appeler les méthodes d’une classe sans connaître le type exact de la classe
  • L’inheritance permet aux classes dérivées de partager les interfaces et le code de leurs classes de base

Il y a des langues où l’inheritance est découplé du polymorphism:

  • En C ++, vous pouvez hériter d’une classe sans produire de comportement polymorphe (c.-à-d. Ne pas marquer de fonctions dans la classe de base avec virtual )
  • En Objective C, vous pouvez implémenter une méthode sur une classe non liée et l’appeler depuis un emplacement ne connaissant que la signature de la méthode.

Pour revenir à Java, la raison d’utiliser le polymorphism est de dissocier votre code des détails de la mise en œuvre de ses contreparties: par exemple, si vous pouvez écrire une méthode Feed(Animal animal) qui fonctionne pour toutes sortes d’animaux, la méthode restrait applicable lorsque vous ajoutez plus de sous-classes ou d’implémentations de l’ Animal . Ceci est en contraste avec une méthode d’ Feed(Dog dog) , qui serait étroitement couplée aux chiens.

Jusqu’au

 Dog d = new Dog(); 

déclaration, il n’y a pas de raison générale pour éviter cela si vous savez que le rest de votre méthode concerne spécifiquement les chiens. Cependant, dans de nombreux cas, ce n’est pas le cas par la suite: par exemple, votre classe ou vos méthodes seraient souvent insensibles à l’implémentation exacte, par exemple

 List numbers = new ArrayList(); 

Dans de tels cas, vous pouvez remplacer new ArrayList() par new LinkedList() et savoir que votre code va être compilé. En revanche, si votre liste de numbers avait été déclarée sous forme de numbers ArrayList numbers , un tel basculement n’aurait peut-être pas été une certitude.

Cela s’appelle “programmation sur une interface”. Il existe une très bonne réponse à Stack Overflow pour l’expliquer.

Vous pouvez avoir d’autres implémentations de la classe Animal , telles que Cat . Alors tu peux dire

 Animal a = new Dog(); Animal b = new Cat(); 

Vous pouvez appeler des méthodes de la classe Animal sans vous soucier de leur implémentation réelle, et le polymorphism appellera la méthode correcte. Par exemple

 a.speak(); // "Woof" b.speak(); // "Meow" 

En réalité, ce n’est pas “Polymorphisme vs Héritage” mais “Polymorphisme utilisant l’Héritage”.

Le polymorphism vous permet d’écrire une méthode qui fonctionne pour n’importe quel Animal :

 public void pet(Animal animal) { ... } 

Cette méthode accepterait Dog , Cat , etc., y compris les sous-classes d’ Animal qui doivent encore être écrites.

Si la méthode devait prendre Dog , cela ne fonctionnerait pas pour Cat etc.

Si vous êtes certain que ce sera toujours un chien, il n’y a aucune raison de le faire. Vous pouvez aussi utiliser Dog d = new Dog (); comme vous l’avez décrit. Mais disons que vous avez utilisé une méthode au lieu d’un constructeur. La méthode renvoyait un animal et vous ne sauriez pas quelle implémentation d’animal vous obtiendriez. Vous pourrez toujours utiliser les mêmes méthodes sur l’animal (même si c’est un chien, un chat éléphant, etc.).

Pour des raisons d’extensibilité, l’inheritance simplifie les choses. Lorsque vous voulez créer un éléphant ou un chat qui partage également certaines méthodes animales, vous pouvez facilement les obtenir en ayant un animal comme super classe.

Normalement, la question que vous avez posée est plus similaire à Inheritance vs Composition :). Un exemple plus concret de la raison pour laquelle il est bon d’utiliser le polymorphism est, par exemple, l’utilisation du modèle de conception de stratégie. Vous pouvez avoir plusieurs implémentations de TaxPolicy: UsaTaxPolicy, CanadaTaxPolicy, EuTaxPolicy, etc. Si vous avez la méthode CalculateFinalPrice, qui doit également calculer la taxe, vous injectez la bonne implémentation et un bon calcul est exécuté, peu importe que vous ayez passé Usa, Canada ou Mise en œuvre de l’ue.

l’inheritance est le polymorphism dynamic. Je veux dire lorsque vous supprimez l’inheritance, vous ne pouvez plus remplacer.