Lors d'une revue de code aujourd'hui, un de mes collègues a dit quelque chose d'intéressant:
prototype
n'est utile que lorsque vous avez besoin d'héritage - et quand l'héritage est-il une bonne idée ?
J'y ai pensé et j'ai réalisé que j'utilisais généralement l'héritage pour contourner le code mal conçu au départ. Le style OO moderne préfère la composition à l'héritage, mais je ne connais aucun langage qui ait pris cela à cœur et qui le fasse réellement respecter .
Existe-t-il des langages de programmation à usage général avec des classes, des objets, des méthodes, des interfaces, etc., qui interdisent l'héritage basé sur les classes? (Si une telle idée n'a pas de sens, pourquoi pas?)
object-oriented
programming-languages
inheritance
Benjamin Hodgson
la source
la source
prototype
est également utile lorsque vous disposez de méthodes et de propriétés publiques qui doivent être partagées entre les instances. Il est également utile car il vous permet d'utiliser correctement l'instanceof
opérateur en JavaScript:if (foo instanceof Foo) { ...
.implements
mot - clé et les interfaces (par opposition à l'héritage d'état et comportement introduit avec l'utilisation duextends
mot - clé sur les classes contenant n'importe quelle implémentation).new
,this
etprototype
sont trop d'un champ de mines pour une utilisation courante par l'OMI.Réponses:
Laissant de côté la question de la définition de la programmation orientée objet, la question devient «y a-t-il des langages qui n'utilisent que la composition et n'ont pas d'outils pour l'héritage?
La réponse à cette question est tout simplement "oui". En route, il n'y a aucun moyen de faire l'héritage comme on le pense classiquement. On peut incorporer un objet dans un autre objet et étendre cet objet. De Object Desoriented Language ( miroir github ):
Vous avez une structure de personne qui a un nom qui est une chaîne. Il a une fonction publique appelée Intro qui renvoie le nom. La structure Woman a également une fonction pour Intro qui accède à la jambe de force qui y est intégrée. Et donc on peut réaliser les intentions d'héritage en utilisant uniquement la composition.
Pour en savoir plus, consultez les didacticiels GoLang: héritage et sous-classe dans Go - ou sa quasi-ressemblance .
Alors oui, il est possible d'avoir un langage OO sans héritage, et il en existe un.
Au sein de Go, cela est connu comme l' intégration et donne aux structures englobantes la possibilité d'accéder aux champs et fonctions intégrés comme si elles les avaient également - mais ce n'est pas une sous-classe. La philosophie de conception se trouve dans la FAQ Go: Pourquoi n'y a-t-il pas d'héritage de type?
la source
typedef
etstruct
en C ...Cela ressemble beaucoup à une description de VBA - Visual Basic pour Applications, intégré à Microsoft Office et à d'autres hôtes compatibles VBA (par exemple AutoCAD, Sage 300 ERP, etc.), ou même VB6. Le "A" de "Basic" signifie "tout usage" de toute façon, il y a donc la partie "polyvalente".
VB6 / VBA a des classes (et donc des objets), des méthodes et des interfaces - vous pouvez définir une
ISomething
interface dans un module de classe comme ceci:Et puis avoir une autre classe qui fait cela:
Une telle classe, n'exposant aucun membre public, ne pourrait être accessible que via son
ISomething
interface - et il pourrait très bien y avoir des dizaines d'implémentations différentesISomething
, donc le code OOP VBA est parfaitement capable de polymorphisme, et il est parfaitement légal pour une classe donnée pour implémenter plusieurs interfaces également.Cependant, VB6 / VBA n'autorise pas l' héritage de classe , vous ne pouvez donc pas hériter d'une implémentation d'un autre type, uniquement son interface. Maintenant, que ce soit un accident, un défaut de conception, un coup de génie ou une énorme oubli laid est ouvert au débat; il n'est pas clair si VB6 / VBA prend cela à cœur , mais il le fait certainement respecter .
Si Go ne fait pas d'héritage de classe et est néanmoins un langage OOP , alors je ne vois pas pourquoi VB6 / VBA ne pourrait pas être considéré comme un langage OOP.
</PreemptiveResponseToVBAHatersThatWillSayItIsNotAnOOPLanguage>
la source
Vous pouvez faire en sorte que le compilateur applique l'héritage sélectif grâce à l'utilisation de techniques privées / protégées et grâce à l'utilisation moderne des techniques "PImpl" ou "Private Implementation".
De nombreuses API exposent uniquement les composants dont vous souhaiteriez qu'un utilisateur hérite et masquent le reste dans une classe d'implémentation distincte. Vous pouvez donc écrire des classes dont les interfaces publiques sont, en fait, non héritables, uniquement utilisables via la composition d'objets et appliquées par le compilateur. C'est souvent une bonne pratique, quand il utilise le compilateur pour appliquer l'intention du logiciel.
Une recherche rapide des fonctions des membres privés en javascript montre qu'il existe un principe similaire, bien que tout le monde puisse voir votre code s'il peut l'utiliser: http://www.crockford.com/javascript/private.html
la source