Delphi-PRAXiS
Seite 2 von 2     12   

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Sonstige Fragen zu Delphi (https://www.delphipraxis.net/19-sonstige-fragen-zu-delphi/)
-   -   Delphi TObject = Object ? (https://www.delphipraxis.net/60141-tobject-%3D-object.html)

Neutral General 3. Jan 2006 18:54

Re: TObject = Object ?
 
Das wird mir langsam zu hoch :mrgreen:
TObject ist für mich ein Mysterium^^

Naja vielleicht nicht mehr soviel wie vor ein paar Minuten aber trotzdem ;)
Danke für die Antworten und den Versuch mir was zu erklären :D

Gruß
Michael

jbg 3. Jan 2006 19:02

Re: TObject = Object ?
 
Zitat:

Zitat von Neutral General
Aber ich meine es wäre logisch wenn TObject = Object wäre und das Object hätte dann halt die ganzen Methoden verpasst bekommen und dann wurden die anderen folgenden Komponenten halt von TObject abgleitet. Was ist denn TObject sonst ?

class und object sind zwei verschienene Konzepte. Das ältere object ist nichts anderes als ein record, der Methoden, eine VMT und eine DMT hat. object Objekte werden immer auf dem Stack oder im Datensegment angelegt, wenn man keine Zeiger-Typ darauf nutzt.
Delphi-Quellcode:
PMyObject = ^TMyObject;
TMyObject = object
  constructor Init(const A: string);
  destructor Done;
  procedure Haha; virtual;
end;

var
  P: PMyObject;
begin
  P := New(PMyObject, Init('Hallo'));
  P^.Haha;
  Dispose(P, Done);
end;
Ein class Objekt liegt immer im Heap (freier Speicher) und nutzt um einiges mehr Compilermagic als das alte object. Das fängt schon beim Konstruktor an, der nicht aus einer Methode besteht sondern aus meheren (NewInstance + Create + AfterConstruction). Der Compiler versteckt das aber vor unseren Augen.

TObject is eine class und kein object. Die beiden Arten von "Klassen" sind nicht binärkompatibel. So liegt bei class die VMT immer an Offset 0, wohingegen bei object die VMT erst dann eingefügt wird, wenn die erste virtuelle Methode zum Objekt hinzukommt. Alle vorher definierten Felder verschieben also den Offset des VMT-Zeigers bei object. Die VMT ist bei class eine Metaklasse (beschreibt also die Klasse selbst). Dies ermöglicht die Nutzung von virtuellen Konstruktoren und virtuellen Klassenmethoden (Stichwort: TClass = class of TObject). Bei object wird die VMT ihrem Namen mehr gerecht, denn dort ist sie nur eine Tabelle der virtuellen Methoden (Virtual Method Table) mit einem zusätzlichen DMT-Zeiger (Dynamic Method Table).

jbg 3. Jan 2006 19:09

Re: TObject = Object ?
 
Zitat:

Zitat von Neutral General
TObject ist für mich ein Mysterium

Der Compiler kompiliert die System.pas in einem speziellen Modus, in dem er einiges anders verarbeitet als wenn man eingene Units kompiliert. Die System.pas und der Compiler hängen so stark zusammen, dass bei Änderungen am Compiler immer auch Änderungen an der System.pas notwendig sind.

TheAn00bis 31. Mär 2006 13:39

Re: TObject = Object ?
 
Zitat:

Zitat von jbg
TObject is eine class und kein object. Die beiden Arten von "Klassen" sind nicht binärkompatibel. So liegt bei class die VMT immer an Offset 0, wohingegen bei object die VMT erst dann eingefügt wird, wenn die erste virtuelle Methode zum Objekt hinzukommt. Alle vorher definierten Felder verschieben also den Offset des VMT-Zeigers bei object. Die VMT ist bei class eine Metaklasse (beschreibt also die Klasse selbst). Dies ermöglicht die Nutzung von virtuellen Konstruktoren und virtuellen Klassenmethoden (Stichwort: TClass = class of TObject). Bei object wird die VMT ihrem Namen mehr gerecht, denn dort ist sie nur eine Tabelle der virtuellen Methoden (Virtual Method Table) mit einem zusätzlichen DMT-Zeiger (Dynamic Method Table).

Heißt das, dass ich ein Objekt (deklariert durch Txyz = Object) nicht erst über das .Create oder einen anderen Konstruktor erzeugen muss, sondern einfach eine Prozedur des Objekts ausführen kann? Oder hab ich das falsch verstanden?

Neutral General 31. Mär 2006 13:46

Re: TObject = Object ?
 
Richtig.
Objecte können proceduren und functionen haben und Variablen. Haben aber von Natur aus keine Variablen oder Methoden genau wie Records. Und man muss sie genauso wie records nicht erstellen, kann aber trotzdem mit proceduren und Functionen arbeiten. Wie es jedoch mit OOP und Vererbung etc aussieht weiß ich nicht.

Beispiel:

Delphi-Quellcode:
 TMensch = Object
  Name: String
  Alter: Word;
  procedure Bewegen(x,y: Integer);
  function Ka: Boolean;
 end;

procedure TForm1.Button1Click(Sender: TObject);
var Ich: TMensch;
begin
  Ich.Name := 'Michael';
  Ich.Alter := 17;
  Ich.Bewegen(MeinZimmer.x,MeinZimmer.y);
end;

TheAn00bis 31. Mär 2006 14:02

Re: TObject = Object ?
 
Hey Danke, spricht abgesehen von
Vererbung etwas gegen die Nutzung
von dieser Art von Objekten?
Aus jbgs Beitrag versteh ich nicht viel. :wink:

jbg 31. Mär 2006 14:04

Re: TObject = Object ?
 
Eine VMT würde keinen Sinn machen, wenn man nicht erben kann:
Delphi-Quellcode:
type
  PFigure = ^TFigure;
  TFigure = object
    X, Y: Integer;

    constructor Init(AX, AX: Integer);
    destructor Done; virtual;
    procedure Draw; virtual;
  end;

  PCircle = ^TCircle;
  TCircle = object(TFigure)
    R: Integer;
    constructor Init(AX, AY, AR: Integer);
    destructor Done; override;

    procedure Draw; override;
  end;

  PRectangle = ^TRectangle;
  TRectangle = object(TFigure)
    X1, Y1: Integer;
    constructor Init(AX0, AY0, AX1, AY1: Integer);
    procedure Draw; override;
  end;

var
  DynFigure: PFigure;
  StaticFigure: TFigure; // behandeln wie einen Record
begin
  DynFigure := New(PRectangle, Init(10, 10, 20, 20));
  DynFigure^.Draw; // zeichnet ein Rechteck
  Dispose(DynFigure, Done);

  StaticFigure.Init(10, 10);
  StaticFigure.Draw; // zeichnet einen Punkt
  StaticFigure.Done;
end.

Neutral General 31. Mär 2006 14:07

Re: TObject = Object ?
 
Übrigens wie ich gerade herausgefunden hab:
Vererbung FUNKTIONIERT !

Die Muhkuh 31. Mär 2006 14:08

Re: TObject = Object ?
 
Aber nicht mit dem Quelltext von jbg.

Neutral General 31. Mär 2006 14:16

Re: TObject = Object ?
 
Delphi-Quellcode:
Gebaeude = Object
   Flaeche: Integer;
   procedure Bauen;
  end;

  Haus = Object(Gebaeude)
   NeNeueVar: String;
   procedure Bauen;
  end;
1. Flaeche existiert auch in der Klasse Haus.
2. Man kann entweder "Bauen" so "überschreiben":

Delphi-Quellcode:
procedure Haus.Bauen;
begin
  Form1.Caption := 'Haus bauen!';
end;
oder/und die Methode einfach vererben:

Delphi-Quellcode:
procedure Haus.Bauen;
begin
  inherited;
  // eventuell weiterer Quelltext
end;


Alle Zeitangaben in WEZ +1. Es ist jetzt 15:38 Uhr.
Seite 2 von 2     12   

Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz