Einzelnen Beitrag anzeigen

Der_Unwissende

Registriert seit: 13. Dez 2003
Ort: Berlin
1.756 Beiträge
 
#3

Re: Fragen zu OOP und Klassen

  Alt 22. Nov 2007, 08:42
Hi, erstmal vorweg finde ich Deine Idee gut, da ich damals (als ich die OOP verstehen wollte) auch kein wirklich gutes Tut. gefunden hatte. Ist allerdings auch ein paar Jahre her, vielleicht sind die ja schon besser geworden. Trotzdem ist es immer gut zu fragen und natürlich werden die Fragen auch gerne beantwortet.

Zitat von Gonzo2:
Wie ich allerdings in vielen Beispielen sehen konnte wird inherited genommen ohne groß zu überlegen. Einen Fehler macht man anscheinend nicht wenn man inherited in eine Klasse einbaut die direkt von TObject abstammt, aber wozu nehmen wenn nicht nötig. Das gleiche gilt wohl auch für Destroy. Eine andere Frage ist wozu inherited bei Create immer vorne und bei Destroy immer hinten genommen wird?
Ganz so sinnlos wie es erscheint ist es nicht. Inherited ruft immer die gleichnamige Methode des Vorfahren auf. Dazu muss man kurz sagen, dass Klassen eben eine Art Tabelle besitzen, in der zu jeder virtuellen Methode ein Verweis existiert. Wird eine virtuelle Methode aufgerufen, so wird in der Tabelle nachgeschlagen, welche Methode verwendet werden soll. Anders als bei statischen Methoden können virtuelle auch durch einen Nachfahren überschrieben (direktive override) werden. Damit ändert man den Eintrag in dieser Tabelle, der verwendet wird. Ebenso kann man Methoden durch eine gleich benannte Methode überdecken. Hier wird in der Tabelle dann geschaut, von welcher "Art" / welchem "Typ" die Klasse ist. Das ist nötig, da jede erbende Klasse auch wie einer ihrer Vorfahren verwendet werden kann (z.B. kann eine TStringList als TStrings oder als TObject verwendet werden). Für jede der möglichen Klassen (also die eigentliche Klasse selbst, sowie alle Vorfahren) existiert dann ein Eintrag in dieser Tabelle für jede Methode.

Hierin liegt auch díe eigentliche Begründung für die Position von inherited. Das Create eines TObject hat die grundlegenden Dinge zu erledigen, es muss Speicher alloziert, diese Tabelle erzeugt und ein Verweis zurückgegeben werden. Vieles von dem Code bleibt aber verborgen, da es sehr spezifisch ist. Deshalb wirkt das Create nur leer, tatsächlich wird auch dort (natürlich) Code ausgeführt. Es macht natürlich für jede Klasse Sinn, dass man erst den nötigen Speicher alloziert usw. und erst dann weitermacht. Dass es auch ohne klappt hat nicht viel zu sagen, das kann auch von Fall zu Fall mal ordentlich nach hinten losgehen. Da gibt es dann eine Access Violation.
Ebenso ist das Destroy von TObject für das Aufräumen des Speichers zuständig. Dabei wird eben das eigentliche Objekt (also z.B. auch die genannte Tabelle) aus dem Speicher entfernt. Entsprechend kannst Du nicht mehr auf das Objekt zugreifen, wenn das inherited Destroy aufgerufen wurde. Die anderen Arbeiten die im (eigenen) Destruktor stattfinden sind i.d.R. das Aufräumen von Datentypen, auf die nur ein Verweis gespeichert wurde (dyn. Arrays, Klassen, Zeiger). Dort würde das inherited sonst nur den Speicher für den Verweis löschen, die eigentlichen "Objekte" (hier nicht im OO-Sinne gemeint) würden einfach unerreichbar im Speicher verbleiben.

So, muss leider gerade los, werde aber bei Gelegenheit mit noch den Rest anschauen und antworten.

Gruß Der Unwissende
  Mit Zitat antworten Zitat