Je connais la syntaxe, les règles appliquées à la classe abstraite et je veux savoir utiliser une classe abstraite
La classe abstraite ne peut pas être instanciée directement mais peut être étendue par une autre classe
Quel est l'avantage de le faire?
Comment est-ce différent d'une interface?
Je sais qu'une classe peut implémenter plusieurs interfaces mais ne peut étendre qu'une classe abstraite. Est-ce seulement une différence entre une interface et une classe abstraite?
Je suis conscient de l'utilisation d'une interface. J'ai appris cela du modèle de délégation d'événements d'AWT en Java.
Dans quelles situations dois-je déclarer la classe comme une classe abstraite? Quels sont les avantages de cela?
java
object-oriented
abstract-class
Vaibhav Jani
la source
la source
Réponses:
Cette réponse explique très bien les différences entre une classe abstraite et une interface, mais ne dit pas pourquoi vous devriez en déclarer une.
D'un point de vue purement technique, il n'est jamais nécessaire de déclarer une classe abstraite.
Considérez les trois classes suivantes:
Vous n'avez pas besoin de rendre la classe Database abstraite, même si son implémentation pose un problème évident: lorsque vous écrivez ce programme, vous pouvez taper
new Database()
et il serait valide, mais cela ne fonctionnerait jamais.Quoi qu'il en soit, vous obtiendriez toujours un polymorphisme. Ainsi, tant que votre programme ne fabrique
SqlDatabase
que desOracleDatabase
instances, vous pouvez écrire des méthodes telles que:Les classes abstraites améliorent la situation en empêchant un développeur d'instancier la classe de base, car un développeur l'a marquée avec une fonctionnalité manquante . Il offre également une sécurité au moment de la compilation, vous permettant ainsi de vous assurer que toutes les classes qui étendent votre classe abstraite fournissent la fonctionnalité minimale nécessaire pour fonctionner, sans avoir à vous soucier de la possibilité d'utiliser des méthodes de stub (comme celle ci-dessus) que les héritiers ont en quelque sorte. comme par magie, ils doivent redéfinir une méthode pour la faire fonctionner.
Les interfaces sont un sujet totalement séparé. Une interface vous permet de décrire les opérations pouvant être effectuées sur un objet. Vous utiliserez généralement des interfaces lors de l'écriture de méthodes, de composants, etc., qui utilisent les services d'autres composants, d'objets, mais vous ne vous souciez pas du type d'objet à partir duquel vous obtenez les services.
Considérez la méthode suivante:
Vous ne vous souciez pas de savoir si l'
database
objet hérite d'un objet particulier, vous vous souciez juste qu'il ait uneaddProduct
méthode. Ainsi, dans ce cas, une interface convient mieux que de faire en sorte que toutes vos classes héritent de la même classe de base.Parfois, la combinaison des deux fonctionne très bien. Par exemple:
Notez que certaines des bases de données héritent de RemoteDatabase pour partager certaines fonctionnalités (comme se connecter avant d'écrire une ligne), mais FileDatabase est une classe distincte à implémenter uniquement
IProductDatabase
.la source
Similitudes
Les classes abstraites et les interfaces sont nécessaires pour l'abstraction. Ils ne peuvent pas être instanciés avec un nouveau , mais peuvent être résolus en inversant des conteneurs de contrôle ou via des modèles d'usine.
Différence
Des interfaces
Classe abstraite
Il est en fait facile de trouver la réponse par simple requête google .
la source
Dans une classe abstraite, vous pouvez implémenter certaines méthodes et laisser (forcer) le reste à mettre en œuvre par la classe étendue. Vous ne pouvez pas implémenter de méthodes dans une interface. Vous ne pouvez forcer personne à ignorer quoi que ce soit lors de l'extension d'une classe ordinaire. Avec une classe abstraite, vous pouvez.
la source
Les classes abstraites sont pour "est un" et les interfaces sont pour "peut faire".
Les classes abstraites vous permettent d'ajouter un comportement de base afin que les programmeurs n'aient pas à tout coder, tout en les forçant à suivre votre conception.
la source
Outre les détails techniques profonds - comme la mise en œuvre de certaines méthodes pour les classes abstraites, etc., le sens est le suivant:
Les interfaces définissent une capacité commune - IEnumerable définit que la classe qui implémente cette interface peut être énumérée. Cela ne dit rien sur la classe elle-même.
Les classes abstraites (ou de base) définissent le comportement - WebRequest définit un comportement commun à toutes les classes enfants telles que HttpWebRequest, etc. Il définit la signification principale de la classe et son objectif réel: accéder aux ressources Web.
la source
Entrée Wikipedia .
La principale différence entre une interface et une classe abstraite réside dans le fait qu’une classe abstraite peut fournir des méthodes implémentées. Avec les interfaces, vous ne pouvez déclarer que des méthodes, écrire leur signature. Voici un exemple de classe qui étend une classe abstraite qui implémente deux interfaces: (java)
Dans cet exemple, MyAbstractClass fournit une méthode publique qui affiche les trois valeurs. Dans ImpClass, vous devez implémenter getValue1 et getValue2 respectivement à partir de MyInterface1 et MyInterface2 et getValue3 à partir de la classe abstraite.
Voilà.
Il y a plus d'aspects (interface: uniquement les méthodes publiques, classe abstraite: méthodes abstraites protégées et abstraites publiques), mais vous pouvez le lire vous-même.
Sur une note finale, une classe abstraite qui fournit uniquement des méthodes abstraites est une classe de base abstraite "pure", également appelée interface.
la source
En d'autres termes, vous devriez commencer par une question: "ces classes partagent-elles nécessairement l' implémentation ou ont-elles simplement une interface commune ?"
Si la réponse est mixte, telle que - ces trois classes doivent partager l'implémentation, mais que ces deux autres ne partagent que leur API - vous pouvez alors créer une interface pour les cinq et une classe abstraite pour ces trois avec le commun code.
Il existe également d'autres méthodes pour partager l'implémentation, par exemple pour encapsuler un objet avec cette implémentation (par exemple, dans le modèle Stratégie ).
la source
Vous déclareriez un résumé de classe lorsque vous ne souhaitez pas que le développeur (probablement vous-même) soit autorisé à l'instancier, car cela ne fonctionnerait pas ou n'aurait pas de sens.
Par exemple, considérons un jeu dans lequel il existe différents types d’entités de jeu. Ils héritent tous de la base
GameEntity
classe de .Cette classe est déclarée
abstract
car cela n'aurait aucun sens de l'instancier. Il déclare certaines actions pour les entités de jeu et certains attributs, mais ces attributs ne sont nulle part dans cette classe initialisés. Cette classe sert de modèle aux entités du jeu, mais n'est pas censée être instanciée par elle-même, et en tant que telle déclaréeabstract
.En ce qui concerne la différence d'utilisation entre une classe abstraite et une interface:
Selon moi, une interface est un moyen d'obtenir un comportement polymorphe sans être limitée par le mécanisme d'héritage unique de certaines langues.
Revenons au jeu à titre d'exemple. Considérons une classe
Enemy
dérivée deGameEntity
. Cette classe a une méthodeattackMeFromDistance(RangedAttacker attacker)
. Cette méthode est destinée à permettre aux entités d’attaquer l’ennemi de très loin.Comme vous pouvez le constater, cette méthode prend un
RangedAttacker
type en tant que paramètre. Cependant, toutes les entités de jeu héritent déjà deGameEntity
. Ils ne peuvent pas prolonger une autre classe.Prenez les cours
Mage
etArcher
par exemple. Nous voulons permettre que les deux soient acceptés comme paramètres de laattackMeFromDistance(RangedAttacker attacker)
méthode, mais ils sont déjà dérivés deGameEntity
.Pour résoudre ce problème, nous créons une nouvelle interface:
Une classe qui implémente cette interface doit implémenter la
attackFromDistance()
méthode et il est donc assuré qu'elle dispose de capacités d'attaque à distance. Cela signifie que laattackMeFromDistance
méthode peut maintenant accepter en toute sécurité les classes qui implémentent cette interface. Donc faireMage
etArcher
mettre en œuvre cette interface résout notre problème.Pour moi, c'est le pouvoir des interfaces.
Donc, pour résumer, vous utiliseriez habituellement une classe abstraite lorsque vous voulez avoir une classe de base pour certaines classes, mais cela n'aurait pas de sens de l'instancier par lui-même (ou dans le cas où il a des
abstract
méthodes, qui doivent être implémenté par les sous-classes, et dans ce cas le compilateur vous obligerait à faire la classeabstract
). Vous utiliseriez une interface pour obtenir un comportement polymorphe sans être limité par le mécanisme d'héritage unique.la source
la source