Warum sind Vererbung, Einkapselung und Polymorphismus nicht die Säulen von OOP? [geschlossen]

16

Eines Tages ging ich zu einem Stapelüberlauf-Chat und sah eine Phrase, die besagte, dass Vererbung, Einkapselung und Polymorphismus die Säulen von OOP sind (in dem Sinne, dass sie grundlegend sind, eine Konstruktionssohle).

Es gibt auch eine ähnliche Frage, die mir bei College-Prüfungen und Vorstellungsgesprächen sehr oft gestellt wurde, und die richtige Antwort war immer die im Titel der Frage ausgesprochene Aussage ("Ja, Vererbung, Verkapselung und Polymorphismus sind die Säulen von OOP ).

Aber im Stapelüberlauf-Chat wurde ich ernsthaft verspottet, die Teilnehmer waren mit einer solchen Aussage überhaupt nicht einverstanden. Also, was ist los mit dieser Aussage?

Scheint Programmierer in postsowjetischen und US-amerikanischen Colleges in verschiedenen Dingen ausgebildet zu sein?

Werden Vererbung, Verkapselung und Polymorphismus von US / UK-Programmierern nicht als die Säulen von OOP angesehen?

PaulD
quelle
7
Ihre Frage hat keinen Kontext. Wir wissen nicht, was die Leute im SO-Chat dachten oder worauf sie reagierten. Vielleicht können Sie einen Link zu dem Gespräch im Chatroom erstellen, damit wir es uns ansehen können? Trotzdem denke ich, dass dies am besten im Chat-Raum gelöst wird, anstatt hier.
Robert Harvey
1
@ Robert, zu viel Zeit vergangen. Ich bezweifle, dass ich überhaupt den Link zum Gespräch finden kann. Aber ich stimme zu, dass der Kontext wichtig ist. Es geht nicht darum, jemandem die Schuld zu geben oder mich als unschuldiges Opfer einer Chat-Aggression zu präsentieren, ich möchte nur die Wahrheit wissen.
PaulD
5
Das Wohnzimmer. Hast du zuerst deinen Flammenschutzanzug angezogen?
Robert Harvey
1
Die einzige Bedeutung, die ich dem Satz geben kann, ist entweder "Sie können OOP ohne einen von ihnen haben" (wahr, macht aber zumindest für die Kapselung keinen Sinn) oder "Sie können sie auch außerhalb von OOP verwenden" oder so ähnlich.
SJuan76
2
Imo OO hat nur eine Säule und das ist: "Staat". Sobald Ihr Gehirn im Zustand denkt, erhalten Sie OO.
Pieter B

Antworten:

40

Werden Vererbung, Verkapselung und Polymorphismus von US / UK-Programmierern nicht als die Säulen von OOP angesehen?

Sie werden von vielen Programmierern als Säulen betrachtet, und viele Colleges lehren OO auf diese Weise.

Leider ist es auch eine kurzsichtige Ansicht.

  • Vererbung ist nur ein Mechanismus zur Implementierung von OOP und kann missbraucht werden, um OOP nicht auszuführen.
  • Encapsulation ist ein Konzept, das sich für die Programmierung aller Art eignet, OOP und nicht.
  • Polymorphismus ist ein Merkmal (?), Das beschreibt, wie sich die Berechnung verhält. Es gibt viele Wege, um Polymorphismus zu erreichen, von denen nicht alle OO-spezifisch sind.

OOP hat sehr wenig Fundament, da es in Wirklichkeit sehr konzeptionell ist: "Gehen Sie auf die Gestaltung Ihres Programms zu, indem Sie die Dinge als Objekte betrachten - zusammenhängende Daten- und Funktionsbündel."

Und während modernes Programmdesign eine schlechte Sicht auf "reine OO- Arbeitsweise " hat, sind sich die meisten erfahrenen Programmierer einig, dass die SOLID-Prinzipien (oder eine Teilmenge davon) bessere Kandidaten für die "Säulen objektorientierter Programmierung" sind (obwohl sie es sind) gut auf Nicht-OOP anwenden). Diese funktionieren überhaupt nicht mit diesen Begriffen. Stattdessen verwenden sie die Konzepte von Softwareentitäten (von denen Objekte eine sind), Schnittstellen (von denen C # / Java / usw. interfaceeine ist), Abstraktion und Untertypisierung (von denen Vererbung eine Form ist).

Telastyn
quelle
10
Anständige Antwort auf eine im Wesentlichen unbeantwortbare Frage.
Robert Harvey
3
Existiert OOP?
Tulains Córdova
5
Ich würde argumentieren, dass nur die Verkapselung eine "Säule" der OOP ist. Der größte Unterschied zwischen OOP und struktureller Programmierung besteht darin, dass Objekte Code und Daten enthalten, nicht nur Daten (z. B. eine klassische C-Struktur). Die beiden anderen Konzepte werden hauptsächlich in OO-Sprachen verwendet, sind jedoch weder auf OO beschränkt noch von OO erforderlich.
3
@Snowman Encapsulation ist auch nicht auf OOP beschränkt. Die Leute implementieren ständig abstrakte Datentypen in C und funktionalen Sprachen.
Doval
2
Und @ JörgWMittag hatte eine gute Antwort in Bezug auf Messaging. Die Idee des Messaging erfordert zwangsläufig eine Kapselung. Nachrichten werden in der Regel an eine Funktion oder Methode eines Objekts übergeben, die dann auf den darin eingekapselten Zustand reagiert. Das heißt nicht, dass Nicht-OO-Sprachen keine Weitergabe oder Verkapselung von Nachrichten haben können, sondern nur, dass dies grundlegende Ideen von OOP sind.
23

tl; dr: Sie können Vererbung ohne OO haben, Sie können Verkapselung ohne OO haben, Sie können Polymorphismus ohne OO haben, Sie können sogar alle drei auf einmal ohne OO haben. Auf der Rückseite können Sie OO ohne Vererbung haben. Außerdem gibt es verschiedene Arten der Einkapselung (ADT-orientiert und OO). IOW ist nicht jede Einkapselung OO.

Lange Version:

Der Begriff "Objektorientierte Programmierung" wurde von Alan Kay erfunden, damit er entscheiden kann, was es bedeutet. Und er definiert es so :

OOP bedeutet für mich nur Nachrichtenübermittlung, lokale Aufbewahrung und Schutz sowie das Verstecken von staatlichen Prozessen und extrem spätes Binden aller Dinge.

In Bezug auf die Implementierung ist Messaging ein spät gebundener Prozeduraufruf. Wenn Prozeduraufrufe spät gebunden sind, können Sie zur Entwurfszeit nicht wissen, was Sie aufrufen werden, sodass Sie keine Annahmen über die konkrete Darstellung des Status treffen können. Es geht also wirklich um Messaging. Late-Binding ist eine Implementierung von Messaging, und die Kapselung ist eine Folge davon.

Später stellte er klar, dass " die große Idee" Messaging "ist, und bedauert, sie" objektorientiert "statt" nachrichtenorientiert "genannt zu haben, weil der Begriff" objektorientiert "den Fokus auf das Unwichtige (Objekte) legt ) und lenkt von dem ab, was wirklich wichtig ist (Messaging):

Nur eine sanfte Erinnerung daran, dass ich bei der letzten OOPSLA einige Anstrengungen unternommen habe, um alle daran zu erinnern, dass Smalltalk nicht nur NICHT seine Syntax oder die Klassenbibliothek ist, sondern nicht einmal Klassen. Es tut mir leid, dass ich den Begriff "Objekte" für dieses Thema vor langer Zeit geprägt habe, weil es viele Leute dazu bringt, sich auf die geringere Idee zu konzentrieren.

Die große Idee ist "Messaging" - darum geht es bei Smalltalk / Squeak (und es ist etwas, das in unserer Xerox-PARC-Phase nie ganz abgeschlossen wurde). Die Japaner haben ein kleines Wort - ma - für "das, was dazwischen liegt" - vielleicht ist das nächste englische Äquivalent "interstitial". Der Schlüssel zur Entwicklung großartiger und erweiterbarer Systeme liegt vielmehr in der Gestaltung der Kommunikation der Module als in der Festlegung der internen Eigenschaften und Verhaltensweisen. Denken Sie an das Internet - um zu leben, muss es (a) viele verschiedene Arten von Ideen und Realisierungen zulassen, die über einen bestimmten Standard hinausgehen, und (b) ein unterschiedliches Maß an sicherer Interoperabilität zwischen diesen Ideen ermöglichen.

(Natürlich konzentrieren sich die meisten Menschen heute nicht mehr auf Objekte, sondern auf Klassen, was noch falscher ist.)

Messaging ist für OO sowohl als Metapher als auch als Mechanismus von grundlegender Bedeutung .

Wenn Sie jemandem eine Nachricht senden, wissen Sie nicht, was er damit macht. Das einzige, was Sie beobachten können, ist ihre Reaktion. Sie wissen nicht, ob sie die Nachricht selbst verarbeitet haben (dh ob das Objekt eine Methode hat), ob sie die Nachricht an eine andere Person weitergeleitet haben (Delegation / Proxying) oder ob sie sie überhaupt verstanden haben. Darum geht es bei der Verkapselung, darum geht es bei OO. Sie können einen Proxy nicht einmal von der Realität unterscheiden, solange er so reagiert, wie Sie es erwarten.

Ein "moderner" Begriff für "Messaging" ist "dynamischer Methodenversand" oder "virtueller Methodenaufruf", der jedoch die Metapher verliert und sich auf den Mechanismus konzentriert.

Ähnliche Punkte finden sich auch in On Understanding Data Abstraction, überarbeitet von William R. Cook, und in seinem Vorschlag für vereinfachte, moderne Definitionen von "Objekt" und "objektorientiert" .

Der dynamische Versand von Vorgängen ist das wesentliche Merkmal von Objekten. Dies bedeutet, dass die aufzurufende Operation eine dynamische Eigenschaft des Objekts selbst ist. Operationen können nicht statisch identifiziert werden, und es gibt im Allgemeinen keine Möglichkeit, genau zu bestimmen, welche Operation als Antwort auf eine bestimmte Anforderung ausgeführt wird, es sei denn, sie wird ausgeführt. Dies ist genau das gleiche wie bei erstklassigen Funktionen, die immer dynamisch abgesetzt werden.

In Smalltalk-72 gab es nicht einmal Gegenstände! Es gab nur Nachrichtenströme, die analysiert, umgeschrieben und umgeleitet wurden. Zuerst kamen Methoden (Standardmethoden zum Parsen und Umleiten der Nachrichtenströme), später kamen Objekte (Gruppierungen von Methoden, die einen privaten Status gemeinsam haben). Die Vererbung erfolgte viel später, und Klassen wurden nur eingeführt, um die Vererbung zu unterstützen. Wäre Kays Forschungsgruppe bereits über Prototypen informiert gewesen, hätte sie wahrscheinlich niemals Klassen eingeführt.

Jeder Programmierer sollte " Über das Verständnis der Datenabstraktion" lesen . Es wird detailliert erläutert, worin genau der Unterschied zwischen Objekten und abstrakten Datentypen besteht. Er gibt Beispiele mit Java, und das ist für diese Frage äußerst relevant, da er sowohl in den ADT-Beispielen als auch in den Object-Beispielen Vererbung, Kapselung und Polymorphismus verwendet, aber nur eines der Beispiele objektorientiert ist! Mit anderen Worten: Sie können Vererbung, Einkapselung und Polymorphismus haben, Sie können sogar alle drei auf einmal haben und haben immer noch keine OO.

Auf der anderen Seite können Sie OO ohne Vererbung haben. Wie ich oben angedeutet habe: Die Originalversionen von Smalltalk (die von Alan Kay, dem Erfinder des Begriffs "objektorientierte Programmierung", entworfene Sprache) hatten keine Vererbung.

Last but not least diskutiert der Vertrag von Orlando die Delegation als Alternative zur Vererbung und wie unterschiedliche Formen der Delegation und Vererbung zu unterschiedlichen Gestaltungspunkten im Gestaltungsraum objektorientierter Sprachen führen. (Beachten Sie, dass die Leute auch in Sprachen, die Vererbung unterstützen, wie Java, tatsächlich lernen, dies zu vermeiden, was wiederum darauf hinweist, dass dies für OO nicht erforderlich ist.)

Jörg W. Mittag
quelle
Sie können "Vererbung", "Polymorphismus" und "Vererbung" haben ... es gibt irgendwo einen Tippfehler :)
Slebetman
1
Diese Antwort lässt mich wünschen, wir könnten auch "Lieblings" -Antworten haben.
Chan-Ho Suh
Die Definition von Alan Kay ist veraltet. OO benötigt Vererbung, und wenn Sie wie in C ++ sowohl Laufzeit- als auch Kompilierungsbindungen ausführen können, erhalten Sie eine Leistung, die der von C ebenbürtig ist.
Erik Alapää
Nein, seine Definition ist die richtige. Sie brauchen überhaupt keine Vererbung, um OO zu sein. Prototypensprachen verwenden keine Vererbung wie C ++ und sind immer noch OO. Vererbung wird nur verwendet, um die Wiederverwendung von Code zu implementieren. Dies ist nicht einmal der beste Weg. Es gibt viele bessere Sprachen, die beispielsweise über Mixins verfügen. Es hat auch nichts mit Binden zu tun, da Sie dynamisches Dispatching haben können, auch nicht in C ++, wenn Sie virtuelle Methoden verwenden können. Leistung hat nichts damit zu tun, das sind Konzepte auf hohem Niveau, sie haben keine Leistung. Tatsächlich könnten Sie die Nachrichtenübermittlung in C implementieren und OO sein
Luiz Felipe