Objekt Orientiertes Denken
StartSeite | Neues | TestSeite | ForumSeite | Teilnehmer | Kategorien | Index | Hilfe | Einstellungen | Ändern
Auf der Seite WarumMussCeeWieModulaAussehen (übriges: Es muss nicht) habe ich die Behauptung aufgestellt, dass es teilweise Widersprüche zwischen ObjektOrientierteProgrammierung und dem gibt, was ich als ObjektOrientiertesDenken bezeichne. Die natürliche kritische Reaktion darauf:
- Interessante Aussage. Wo liegen denn die Widersprüche?
läßt sich besser auf einer eigenen Seite beantworten. Zumindest möchte ich es hier versuchen.
ObjektOrientiertesDenken ist AFAIK kein fachlich definierter Begriff. Wenn er mir bisher begegnet ist, dann in einer naiven Form wie "es ist nicht leicht sich auf objektorientiertes Denken umzustellen", also als synonym für "Denken in den Bahnen einer objektorientierten Sprache". In dieser Form leistet der Begriff nichts, es könnte auch keine Gegensätze geben. Ich nehme aber mein Recht in Anspruch, diesen Begriff mit mehr Leben zu füllen und damit - wenn geht - etwas nützliches anzufangen. Wenn mir als Praktiker entgangen sein sollte, dass irgendjemand ähnliches getan hat, oder dass der Begriff schon fest definiert ist, dann wäre ich für Hinweise dankbar und dann müsste man schauen, wie weit Übereinstimmung besteht. Bis dahin entwickle ich meine Gedankengänge frei von äußeren Restriktionen.
ObjektOrientiertesDenken ist vor allem einmal "Denken" und nicht "Programmieren". Es ist frei von den Denkgewohnheiten, wie sie sich durch die Verwendung von OO Programiersprachen bilden und damit grundsätzlich auch dem Nichtprogrammierer zugänglich. Vielleicht könnte man es in einer Liga mit "linearem Denken" oder "vernetztem Denken" oder anderen strukturell geprägten Denkformen sehen. Praktisch bedeutet ObjektOrientiertesDenken, dass die Welt (philosophische Ebene) als System von Objekten betrachtet wird. ObjektOrientiertesDenken heißt: Die Welt als Summe von Objekten, ihre Eigenschaften, Veränderungen, Transformationen und Beziehungen zu verstehen.
- [Jetzt brauche ich schön langsam eine Abkürzung und nachdem OOD schon für ObjektOrientiertesDesign? steht, bleibt mir wohl nur OOT (Object Oriented Thinking).]
Wenn diese Konzept möglich ist, dann bewegt sich OOT auf einer anderen Ebene als ObjektOrientierteProgrammierung (OOP). Das bedeutet, dass Widersprüche zwischen OOT und OOP auftreten können bzw. dass sogar eine Kritik von OOP durch OOT möglich wäre. Derzeit ist das ja kaum möglich, weil OOP primär kein theoretisches Konzept ist, sondern in Form spezieller Programmiersprachen (wie Smalltalk, C++, Java, C#) auftritt. Eine konzeptionelle Auseinandersetzung ist immer mit Firmen- und Marktinteressen verknüpft und nie annähernd objektiv (siehe PissingContest). OOT schafft eine anderen Blickwinkel, der sich nicht so ohne weiteres schubladisieren lässt.
Das Ziel von OOT ist aber nicht die Kritik von OOP, sondern ein besseres Verständnis für die Welt und die Probleme die beim Modellieren der Welt (beim Programmieren) entstehen. OOT kann IMO helfen in jeder Sprache Probleme effizienter zu lösen. Die Lösung wird immer in gewisser Weise objektorientiert sein - weil OOT dahintersteht - auch wenn die Sprache prozedural ist.
ObjektOrientiertesDenken heißt:
- Objekte identifizieren ("Das Ding dort nenne ich Haus")
- Das Beispiel scheint mir bereits weiter zu gehen und eher einer Klassifizierung zu entsprechen. Identifizierung würde für mich bedeuten "Diese Ansammlung von Ziegelsteinen mit Stroh oben drauf scheint eine logische Einheit zu bilden". Und dann gibt es da noch die Diskriminierung ("Das ist 'unser Ferienhaus'") -- IljaPreuß
- Eigenschaften der Objekte identifizieren ("Was macht einen Fisch aus?")
- Scheint mir eine Art ReverseEngineering? - schließlich brauchen wir ja bereits gewisse Kriterien für das Fischsein eines Objektes, um überhaupt entscheiden zu können, ob etwas ein Fisch ist.
- Eigenschaften in Erfahrung bringen ("Welche Temperatur hat das Badewasser")
- Eigenschaften ändern ("Wie ändere ich die Farbe meines Hauses?")
- allgemeiner: was kann ich mit dem Objekt tun, und wie reagiert es darauf?
und sich überlegen
- wie sich Objekte verändern ("wie altert ein Mensch?")
- wie Objekte mit anderen Objekten wechselwirken ("Wie funktioniert Fußball?")
und natürlich
- wie Objekte erzeugt werden ("Wie baue ich ein Haus?")
- Wie Objekte zerstört werden ("Wie kündige ich einen Mietvertrag?")
Das ist einfach und das kann auch jeder Nichtprogrammierer verstehen.
(Ein Nebengedanke: Interessanterweise sind im OOT Objekte etwas Fundamentaleres als Klassen. Die Objekte sind real, die Klassen aber etwas künstliches, das wir mit unserem Denken erzeugen: Als Abstraktion für Gruppen von Objekten ähnlicher Eigenschaften. In der OOP ist es umgekehrt: kein Objekt ohne zuvor definierte Klasse.)
- Ich sehe da keine großen Unterschied: In der Programmierung geht es ja darum, etwas zu erschaffen, und zwar im Allgemeinen auf eine reproduzierbare Weise. Bei solcher Zielsetzung gehen wir aber auch außerhalb der Programmierung so vor, dass wir erst eine abstrakte Idee von dem entwickeln, was wir schaffen wollen, bevor wir uns daran machen, ein entsprechendes Ding zu kreieren (das Objekt). Nur sind wir als Programmierer halt in der glücklichen Lage, den lästigen Akt des Produzierens der Maschine überlassen zu können.
Der Mensch denkt automatisch objektorientiert - auch wenn ihm das nicht theoretisch bewußt sein mag - weil ihm nie etwas anderes begegnet. Er begegnet Objekten, die er erkennt oder benennt. Er weiß um ihre Eigenschaften oder erwartet diese Eigenschaften ergründen zu können. Er erwartet mit den Objekten umgehen zu können. Ich postuliere einmal, dass das die natürliche Erwartungshaltung objektorientierten Denkens ist. Nur ganz besondere Umstände können das verhindern: früher Anlass für göttliche oder magische Interpretationen von Sonne, Sterne, Blitz und Donner.
Wenn OOT Erwartungen einen universellen Charakter haben, dann muss es auch dem Programmierer erlaubt sein, die gleichen Erwartungen in Bezug auf die Objekte seiner Programmierumgebung zu haben. Es ist natürlich, dass wir Objekte erwarten, dass wir Eigenschaften erwarten und - wenn keine höhere Gewalt vorliegt - auch Möglichkeiten erwarten vorhandene Eigenschaften zu erfahren und ändern zu können und generell mit den Objekten umgehen zu können.
Objekte sind aber in diesem Sinne nicht nur die Objekte der OO Programmierung (FormaleObjekte?), sondern auch andere tatsächlich vorhandene und beobachtbare Objekte.
So trivial das Ganze ist, zeichnet sich mir da ein ziemlich scharfes Werkzeug ab, um unabweisbare Forderungen an Programmierumgebungen oder APIs zu formulieren: wenn es Objekte im System gibt, dann muss auch für sinnvolle Interaktionsmöglichkeiten gesorgt sein. Andernfalls ist das Design mangelhaft.
Das ist ein Riesenschritt. Normalerweise geht es bei Software um die Erfüllung von Spezifikationen. Nur wenn eine Spezifikation nicht erfüllt ist, ist ein Mangel vorhanden. Gemäß OOT kann ein Mangel aber auch dann vorhanden sein, wenn alle Spezifikationen erfüllt sind. Und das hat nicht mit objektorientierter Programmierung zu tun, sondern mit den Objekten und den vorhandenen Interaktionsmöglichkeiten.
- Könntest Du ein Beispiel dafür geben, wie eine Software, die ihre Spezifikation erfüllt, Mängel bezüglich OOT aufweist und inwiefern es erstrebenswert ist, diese Mängel zu beseitigen?
Die folgenden kritischen Beispiel sollen nicht dazu dienen irgendein System schlecht zu machen. Ich nehme absichtlich Beispiele aus C und Java, weil das jene Sprachen sind, denen ich am meisten zugeneigt bin.
Ein erstes C-Beispiel:
Objekt: der dynamische allokierte Speicherblock.
Eigenschaften:
- die Adresse dient in Doppelfunktion als Objektreferenz
- get: die Adresse ist unmittelbar zugänglich
- set: nicht sinnvoll änderbar, da der Objektbezug verloren wäre
- die Größe
- get: nicht zugänglich, obwohl im System verwaltet
- set: Größe mit realloc änderbar
Aus OOT-Sicht ergibt sich ein Mangel im Design, da die Größe des Speicherblocks nicht mit Hilfe der Objektreferenz auslesbar ist. Da es keine vorzeigbaren Grund, keine "höhere Gewalt" gibt, die diese Lücke rechtfertigt, handelt es sich um einen Mangel im Sinne des OOT. Übrigens wird diesem Mangel des Standard in vielen Compilern durch jeweils eine entsprechende Zusatzfunktion abgeholfen.
Ein weiteres C-Beispiel:
Objekt: der File.
Die Situation ist ein wenig kompliziert, weil bei manchen C-Funktionen (das ist aber auch in anderen Programmiersprachen so) der Name, in manchen ein Filepointer, in den POSIX-Varianten (die ich gleich mitbetrachte) ein Filehandle als Objektreferenz verwendet wird.
Eigenschaften:
- der Name dient in manchen Funktionen als Objektreferenz
- Der Name kann verändert werden. Wenn er nicht als Objektreferenz dient, ist er über die Objektreferenz (Pointer, Handle) nicht zugänglich.
- der Inhalt
- Lesen und Schreiben wird optimal unterstützt
- die Größe
- In den C-Funktionen nicht portabel abfragbar, nur indirekt über schreiben änderbar. In den POSIX-Funktionen abfragbar, nicht portabel änderbar. Es existieren meist Zusatzfunktionen oder Hacks (z.B. schreiben mit Länge 0) um dieses lästige Manko zu umgehen.
Ohne jetzt auf die komplexe Details einzugehen, bestehen aus Sicht von OOT Mängel vor allem in der Behandlung der Eigenschaft Größe (es fehlen FileGetSize und FileSetSize).
Ein Java-Beispiel:
Das Objekt: Der Garbage-Collector.
Eigenschaften:
- Minimale Größe des verwalteten Speichers
- Maximale Größe des verwalteten Speichers
- Aktuelle Größe des verwalteten Speichers
- Freier Anteil im verwalteten Speicher
- Zustand der Aktivität
Die Behandlung des GC als Objekt in Java ist aus Sicht des OOT ein einziger Mangel. Nicht nur, dass er nicht als formales Objekt existiert, es sind auch seine Eigenschaften nur zum geringen Teil abfragbar, änderbar; sein Aktivität kaum steuerbar (Details können ergänzt werden, dienen aber nur der Peinlichkeit).
Das objektorientierte Denken existiert unabhängig von Computer und Programmierung. Deshalb sind Objekte des OOT reale Objekte mit realen Eigenschaften. Wie diese im Computer modelliert werden, ist zwar nicht nebensächlich, aber aus Sicht des OOT ein Implementierungsdetail. So ist es unwesentlich, ob z. B. bei der Handhabung eines realen Objektes File ein formales Objekt zugrunde liegt, oder nicht, solange nur z.B. die Objekt-Eigenschafts-Beziehung klar ausgedrückt ist:
| FileDelete("xy.tmp");
FileSetSize("xy.tmp",1024);
executable=FileIsExecutable("script.pl");
if(FileExist("xy.tmp")) ...
oder (wortreicher):
FileByNameDelete("xy.tmp");
FileByNameSetSize("xy.tmp",1024);
executable=FileByNameIsExecutable("script.pl");
if(FileByNameExist("xy.tmp")) ... |
|
|
Natürlich existiert in jeder Programmiersprache der File auch als referenziertes Objekt (über einen Pointer, eine Nr, einen Filehandle) bzw. im OOP auch als formales Objekt.
- Das, was Du hier als Objekt bezeichnest, ist in nicht-OOP-Sprachen aber auf reine Daten reduziert. Ein solches File-'Objekt' weiß nichts darüber, wie es z.B. geöffnet oder geschlossen wird, das wird in diesem Fall außerhalb des 'Objekts' definiert. Damit geht der OOT-Gedanke verloren, dass ein Objekt auf die Dinge reagiert, die ich mit ihm anstelle; es verkommt zu einem vollkommen passiven Daten-Bündel. -- ip
Oft können auch ähnliche Funktionen mit verschiedener Referenzierungsart existieren:
| file.appendStr(string);
FileAppendStr("app_error_log",message); |
|
|
Eine ganz ähnliche Situation kann im Datenbankbereich entstehen. Gedanklich sind ja die meisten Datensätze Modelle für reale Objekte, z.B. für Kunden. Funktionen wie:
| CustomerIdSetAddress(id,address);
customer.setAddess(address) |
|
|
sind Teil objektorientierter Arbeitsweise, egal ob die Formulierung prozedural oder mittels formaler Objekte erfolgt.
Der Nachteil von OOP ist, dass unausweichlich alles Programmierte in Form von Klassen und Objekten entsteht. Das täuscht eine formale Qualität vor, die inhaltlich oft nicht vorhanden ist. OOP Klassen und Objekte sind häufig nicht Ausdruck klaren objektorientierten Denkens. Der Wunsch die Qualität des durch OOP entstandenen Strukturen zu hinterfragen, besteht weder beim Hersteller (Sprache, Entwicklertools) noch beim professionellen Anwender (SoftwareEntwickler). Beide sind glücklich sich gegenseitig zu bestärken, dass mit OO Technologie - wie immer sie heißen mag - automatisch bessere Qualität entsteht.
- Ich möchte behaupten, dass Programmcode generell häufig nicht Ausdruck klaren Denkens ist. Dies als Nachteil von Programmcode hinzustellen fände ich aber ein bisschen weit hergeholt.
- Natürlich sollte jedem klar sein, dass weit mehr dazu gehört, objektorientiert zu programmieren, als einfach in einer OO-Sprache zu entwickeln.
- Noch bis vor einigen Monaten hätte ich behauptet, dass der Unterschied zwischen prozeduraler und objektorientierter Programmierung eigentlich gar nicht besonders groß ist - aus syntaktischer Sicht ist diese Aussage auch naheliegend, schließlich werden Prozeduren einfach nur an anderer Stelle definiert und Methoden genannt. Heute weiß ich, dass ich immer noch gerade erst dabei bin zu verstehen, was OOP wirklich ausmacht und wie man OO Technologie effektiv einsetzt. Dennoch bin ich davon überzeugt, dass jeder Schritt in Richtung dieser Erkenntnis mir hilft, effizienter bessere Software zu produzieren. -- ip
Hier fehlt eine Definition des Begriffs "Objekt". Objekte werden durch Beispiele eingeführt, und man kann das ziemlich als "alles ist ein Objekt" lesen. Wenn alles ein Objekt ist, ist aber die Behauptung, alle Menschen würden objektorientiert denken, trivialerweise wahr und nutzlos.
Links:
KategorieOop
StartSeite | Neues | TestSeite | ForumSeite | Teilnehmer | Kategorien | Index | Hilfe | Einstellungen | Ändern
Text dieser Seite ändern (zuletzt geändert: 16. Juli 2012 9:44 (diff))