Schritt für Schritt zur klassenbasierten Programmierung - Teil 2

Für Fragen von Einsteigern und Programmieranfängern...
Antworten
Benutzeravatar
fliegermichl
Lazarusforum e. V.
Beiträge: 1639
Registriert: Do 9. Jun 2011, 09:42
OS, Lazarus, FPC: Lazarus Fixes FPC Stable
CPU-Target: 32/64Bit
Wohnort: Echzell

Schritt für Schritt zur klassenbasierten Programmierung - Teil 2

Beitrag von fliegermichl »

Im vorherigen Post hatten wir festgestellt, daß man einen Record direkt verwenden kann, wohingegen eine Klasse erst erzeugt werden muß.

Nun war der Record im letzten Post recht klein und hatte nur 2 Felder. Im echten (Programmierer) Leben hat man es aber oft mit sehr umfangreichen Records, die z.T. noch Unterstrukturen enthalten, zu tun.

Wenn ich in einer Procedure eine Variable oder einen Parameter des Typs des Records definiere, dann reserviert der Compiler für diese Variable soviel Speicher auf dem Stack, wie für die gesamten Daten des Records benötigt werden. Wird ein Parameter des Recordtypen an eine lokale Variable des gleichen Typs übergeben, dann wird der Inhalt des gesamten Records kopiert.

Code: Alles auswählen

procedure Ausgabe(Beispiel : RBeispiel);
begin
 writeln(Beispiel.Name, ' ', Beispiel.Alter);
end;
Das selbe nochmal für die Klasse

Code: Alles auswählen

procedure Ausgabe(Beispiel : TBeispiel);
begin
 writeln(Beispiel.Name, ' ', Beispiel.Alter);
end;
Kein Unterschied zu erkennen?
Wenn Ausgabe mit dem Record aufgerufen wird, dann reserviert der Compiler Speicher für den gesamten Inhalt des Records.
Dann wird der gesamte Record in diesen reservierten Speicher kopiert und dann erst erfolgt der Aufruf der Procedure.
Bei umfangreichen Records und entsprechend häufigen Prozeduraufrufen verlangsamt das den Programmablauf enorm.

Im Fall der Ausgabe mit der Klasse kann der Aufruf direkt erfolgen, da die Klasse im sog. Heapspeicher angelegt wurde und nur die Adresse der Instanz übergeben werden muß.

Aber die Klassen können noch viel mehr!
Mehr dazu im nächsten Post.

Benutzeravatar
corpsman
Lazarusforum e. V.
Beiträge: 1617
Registriert: Sa 28. Feb 2009, 08:54
OS, Lazarus, FPC: Linux Mint Mate, Lazarus GIT Head, FPC 3.0
CPU-Target: 64Bit
Wohnort: Stuttgart
Kontaktdaten:

Re: Schritt für Schritt zur klassenbasierten Programmierung - Teil 2

Beitrag von corpsman »

Man könnte aber auch anmerken das dies am CallByValue liegt, würde der Record via CallByReference übergeben werden, würde der Stack nicht wirklich belastet werden:

Code: Alles auswählen

procedure Ausgabe(Const Beispiel : RBeispiel);
begin
 writeln(Beispiel.Name, ' ', Beispiel.Alter);
end;
Nicht falsch verstehen, ich finde Klassen gut und setze sie Massivst ein, aber aben aufgrund der Kapselung und besseren Zuordnung der Methoden zu den Daten...
--
Just try it

Antworten