AW: Constructor in der Vererbung
Nicht ganz. Innerhalb einer Unit ist Private wie Public, weswegen auch das Strict Private erfunden wurde.
|
AW: Constructor in der Vererbung
Zitat:
Man kann das Verhalten von Private innerhalb einer Unit auch als Designfehler betrachten, der aus Kompatibilitätsgründen nicht direkt behoben werden konnte. Die Einführung von Strict Private als echtes Private war sozusagen die Konsequenz. Wenn ich sehe, daß auf Private Member von außerhalb der eigenen Klasse zugegriffen wird, ist das eigentlich ein Fall für ein Refactoring. Leider ist das auch im Delphi-eigenen Source viel zu weit verbreitet. |
AW: Constructor in der Vererbung
Zitat:
In Delphi bleibt einem da leider nichts anderes übrig, als die beteiligten Klassen in dieselbe Unit zu packen und dort auf private oder protected Member zuzugreifen. |
AW: Constructor in der Vererbung
Zitat:
Delphi-Quellcode:
Edit - Anmerkung: Ich habe nur das von der IDE vorgefertigte Projekt ergänzt und gekürzt. Das es als Programm so nicht laufen kann, ist mir klar.
type
TForm1 = class(TForm) protected Procedure ProtectedProc(); end; var Form1: TForm1; implementation Procedure TForm1.ProtectedProc(); begin end; procedure Main(); begin Form1.ProtectedProc(); // kein Fehler !!! end; |
AW: Constructor in der Vererbung
Das stimmt nicht ganz. Abgeleitete Klassen können auf private Felder/Methoden nur dann zugreifen, wenn sie in derselben Unit deklariert sind. Für protected Members gilt das nicht.
|
AW: Constructor in der Vererbung
Dann wären da noch Tricksereien mit Klassenhelfern und Interposer-Klassen (die ja grade wegen dem "oder selbe Unit"-Prinzip funktionieren).
Die Sichtbarkeitsmodifikatoren einmal überarbeiten- Das ist mein #1-Feature was mir in der Sprache Delphi/Object Pascal am meisten fehlt. Bitte gebt mir vernünftige Namespaces und einen Sichtbarkeitsmodifikator der dem "internal" in C# bzw dem "Default" in Java entspricht. Und damit bitte gleich ein
Delphi-Quellcode:
8-)
uses System.Generics.*
C++ hat zwar auch nur public, private und protected aber wenigstens noch vernünftige Namespaces und im Notfall ein "using". In Pascal gewinnt einfach nur der letzte Import- Und man bekommt noch nicht einmal eine Compilerwarnung wenn eine Unit Symbole einer anderen einfach verdeckt. Das finde ich schon ziemlich hart. |
AW: Constructor in der Vererbung
Ich muss das ursprüngliche Thema noch mal aufgreifen, da ich noch ein paar Probleme habe, die ich mir nicht erklären kann.
Hier noch mal meine Klassen:
Delphi-Quellcode:
Die Funktionen dazu
type
TBefehl = class(TObject) private fGuid: AnsiString; fZeilen: Integer; fZeilenText: AnsiString; fFirstRow: Integer; fLastRow: Integer; fElseRow: Integer; FBlockGuid: AnsiString; FIsInBlock: Boolean; FIsInElse: Boolean; published property Zeilen: Integer read fZeilen write fZeilen; property ZeilenText: AnsiString read fZeilenText write fZeilenText; property FirstRow: Integer read fFirstRow write fFirstRow; property LastRow: Integer read fLastRow write fLastRow; property ElseRow: Integer read fElseRow write fElseRow; property IsInBlock: Boolean read FIsInBlock write FIsInBlock; property IsInElse: Boolean read FIsInElse write FIsInElse; property GUID: AnsiString read fGuid write fGuid; property BlockGuid: AnsiString read FBlockGuid write FBlockGuid; public constructor Create; procedure WriteBefehlToStream(Stream: TStream); procedure ReadBefehlFromStream(Stream: TStream); end; type TECHO = class(TBefehl) private fOn: Boolean; fOff: Boolean; fAt: Boolean; fText: AnsiString; procedure SetRow(Row: Integer); function GetRow: Integer; procedure SetIsInBlock(Value: Boolean); function GetIsInBlock: Boolean; procedure SetIsInElse(Value: Boolean); function GetIsInElse: Boolean; procedure SetBlockGuid(Value: Ansistring); function GetBlockGuid: Ansistring; public procedure BuildZeilenText; procedure WriteToStream(Stream: TStream); procedure ReadFromStream(Stream: TStream); published property IsOn: Boolean read fOn write fOn; property IsOff: Boolean read fOff write fOff; property IsAt: Boolean read fAt write fAt; property Text: AnsiString read fText write fText; property Row: Integer read GetRow write SetRow; property localIsInBlock: Boolean read GetIsInBlock write SetIsInBlock; property localIsInElse: Boolean read GetIsInElse write SetIsInElse; property localBlockGuid: AnsiString read GetBlockGuid write SetBlockGuid; end;
Delphi-Quellcode:
in der Formunit geht's dann folgendermaßen:
procedure TECHO.SetRow(Row: Integer);
begin fFirstRow:=Row; fLastRow:=Row; fElseRow:=-1; fIsInBlock:=False; fIsInElse:=False; fBlockGuid:=''; end; function TECHO.GetRow: Integer; begin Result:=fFirstRow; end; procedure TECHO.SetIsInBlock(Value: Boolean); begin self.FIsInBlock:=Value; end; function TECHO.GetIsInBlock: Boolean; begin Result:=Self.FIsInBlock; end; procedure TECHO.SetIsInElse(Value: Boolean); begin self.FIsInElse:=Value; end; function TECHO.GetIsInElse: Boolean; begin Result:=self.FIsInElse; end; procedure TECHO.SetBlockGuid(Value: AnsiString); begin self.FBlockGuid:=Value; end; function TECHO.GetBlockGuid: AnsiString; begin Result:=self.FBlockGuid; end; procedure TECHO.BuildZeilenText; begin if (Self.fOn and not Self.fOff) then Self.ZeilenText:='ECHO On' else if (not Self.fOn and Self.fOff) then Self.ZeilenText:='ECHO Off' else if (not Self.fOn and not Self.fOff) then Self.ZeilenText:='ECHO '+self.fText; if self.fAt then Self.ZeilenText:='@'+Self.ZeilenText; self.Zeilen:=1; end;
Delphi-Quellcode:
BefehlsList ist eine TObjectList.
echo:=TECHO.Create;
echo.IsOn:=frm_echo.rb_echoon.Checked; echo.IsOff:=frm_echo.rb_echooff.Checked; echo.IsAt:=frm_echo.chk_at.Checked; echo.Text:=frm_echo.edt_eigenerText.Text; echo.BuildZeilenText; if (chk_anfuegen.Checked) or (lst_batch.Items.Count=0) then begin BefehlsListe.Add(echo); ActRow:=BefehlsListe.Count-1; end else begin begin echo.localIsInBlock:=InBlock; echo.localIsInElse:=InElse; echo.localBlockGuid:=Blockguid; BefehlsListe.Insert(IndexOfBefehlGuid(BefehlguidListe[ActRow]), echo); Nun mein Problem: Bis zum "BefehlsListe.Insert" funktioniert alles. D.h. alle Properties werden wie gewünscht gesetzt, das habe ich im Debugger kontrolliert. Wenn ich mir nach dem Insert mein Object "echo" im Debugger ansehe, dann die die Properties "IsInBlock, IsInElse und Blockguid" immer auf False bzw '' , egal was ich vorher gesetzt habe. Ich komme aber nicht dahinter, warum das so ist. Interessanterweise ist der Zeilentext, der ja auch in der Klasse TBefehl deklariert ist, noch dem Insert noch vorhanden. Bitte nicht über den Sinn der Funktionen oder Propertynamen diskutieren, ist eh nur ein Spass- und Übungsprojekt. |
AW: Constructor in der Vererbung
Wird vielleicht SetRow aufgerufen?
|
AW: Constructor in der Vererbung
Zitat:
(Typisch Uwe...kurz und knapp und immer auf den Punkt;-) ) Das sucht man Stundenlang, und hat's vor Augen.....(kopfschütteln). Hab schon in den Tisch gebissen, weil ich immer nach einem Fehler in der Definition gesucht habe. Ich mach besser mal Schluss für heute :-D |
AW: Constructor in der Vererbung
Am Rande: Dein BefehlsList ist noch die alte TObjectList und nicht die aus System.Generics.Collections, oder?
Auch: Kannst du nicht im Debugger weiter hineingehen (F7), was darin jetzt mit deinem Objekt angestellt wird? Und: Ich habe jetzt nicht lange darüber gebrütet, aber GUID, Methoden zum Index suchen, usw- Hast du dir mal das TDictionary angeschaut? |
Alle Zeitangaben in WEZ +1. Es ist jetzt 19:23 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz