![]() |
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
Reintroduce ist nicht das selbe wie override! Denn dann steht in der VMT immer noch die alte Methode TComponent.Notification, und das willst du ja gerade vermeiden. Reintroduce überschreibt eben nicht, wie man schon am Namen sieht.
|
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
If-Struktur geändert.
Ja, ich hatte die If-Struktur einfach von "TControl.Notification" übernommen. Hab endlich auch einen sehr kurzen Text in meinem Handbuch gefunden, wo selbes wie bei TControl Konstrukt beschrieben ist.
Delphi-Quellcode:
Die Komponente, die gelöscht werden soll, kann nicht "nil" sein. Dann wurde sie ja bereits gelöscht.
procedure TDkComponent.Notification
( pComponent : TComponent; pOperation : TOperation ); begin inherited Notification( pComponent, pOperation ); if ( pOperation = opRemove ) and ( pComponent = Self.FComboBox ) then Self.FComboBox := nil; end; Allerdings verstehe ich auch nicht, warum mit der Eigenschaft "ComboBox" anstelle der privaten "FComboBox" gearbeitet wurde. Mein Problem ist aber (in diesem Beispiel nicht), dass ich oft Methoden mit komplett neuen Parametern überschreibe. Meistens sind es die Konstruktoren. Da funktioniert "override" nicht. Aber ich will eben auch keine Methode mit neuem Namen implementieren. Gerade Create sollte auch Create bleiben. Gibt es noch eine 4. Möglichkeit? |
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
Override ist ein Schlüsselwort, dass nicht ersetzt werden kann. Es gibt keine Alternative dazu.
|
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
Aus der Doku:
Delphi-Quellcode:
Allerdings ist die geebrte Methode immer noch verfügbar, also nicht wirklich überschrieben.
T1 = class(TObject)
procedure Test(I: Integer); overload; virtual; end; T2 = class(T1) procedure Test(S: string); reintroduce; overload; end; // ... SomeObject := T2.Create; SomeObject.Test('Hello!'); // calls T2.Test SomeObject.Test(7); // calls T1.Test Kannst Du mir bitte in knappen Worten beschreiben, wozu Methoden versteckt werden müssen? Wenn es nicht zu groß ist das Thema. Ach verdammter Mist! Ich hätte dem Thema der OOP mehr Achtung schenken sollen. :wall: Mir fehlt einfach das nötige Wissen zu grundlegenden Konzepten. Wie ärgerlich, egal in welcher Progr.-Sprache. Werde wohl noch mal Tutorials pauken. :!: |
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
Beispiel:
Delphi-Quellcode:
Getippt und nicht getestet.
program VirtualMethodsTest;
type TAncestor = class procedure TestMethod; virtual; end; TDescendent = class(TAncestor) procedure TestMethod; override; {testweise durch reintroduce ersetzen} end; procedure TAncestor.TestMethod; begin Writeln('TAncestor.TestMethod'); end; procedure TDescendent.TestMethod; begin Writeln('TDescendent.TestMethod'); end; var Inst: TAncestor; begin Inst := TDescendent.Create; try Inst.TestMethod; finally Inst.Free; end; end. Du wirst einen Unterschied erkennen, wenn du override durch reintroduce ersetzt. |
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
OK. Alles klar. Jetzt weiß ich, wo meine Lücke war. Ich hatte den Fall so konkret noch nicht. Ich habe es immer vermieden die Nachfahren-Methoden aus dem Vorfahren heraus aufzurufen.
Ich habe Dein Lernbeispiel mal experimentell erweitert und ... naja, in Worte fassen kann ich es auch nicht. Das habe ich schon versucht. Aber ich habe es klar verstanden.
Delphi-Quellcode:
Alles klar! Ein wirklich interessantes Konstrukt. Die Frage ist nur, ob sowas Sinn macht. Wenn es einen wirklich wichtigen Anwendungsfall dafür gibt (HAHA), so sind Java und Andere im deutlichen Nachteil, da diese alle Methoden nativ als virtuell deklarieren.
program test;
type TA = class procedure Test; virtual; end; TD1 = class( TA ) procedure Test; reintroduce; end; TD2 = class( TA ) procedure Test; override; end; TD3 = class( TD1 ) procedure Test; virtual; end; TD4 = class( TD3 ) procedure Test; override; end; procedure TA.Test; begin WriteLn( 'A' ); end; procedure TD1.Test; begin WriteLn( 'D1' ); end; procedure TD2.Test; begin WriteLn( 'D2' ); end; procedure TD3.Test; begin WriteLn( 'D3' ); end; procedure TD4.Test; begin WriteLn( 'D4' ); end; var Inst1 : TA; Inst2 : TD3; begin Inst1 := TD1.Create; try Inst1.Test; finally Inst1.Free; end; Inst1 := TD2.Create; try Inst1.Test; finally Inst1.Free; end; Inst1 := TD3.Create; try Inst1.Test; finally Inst1.Free; end; Inst1 := TD4.Create; try Inst1.Test; finally Inst1.Free; end; Inst2 := TD3.Create; try Inst2.Test; finally Inst2.Free; end; Inst2 := TD4.Create; try Inst2.Test; finally Inst2.Free; end; end. ![]() Vielen herzlichen Dank für den Codeschnipsel. Der erklärte mir alles. :thumb: Jetzt fällt mir nach 12 Jahren alles wieder ein. Edit: Nun muss ich ja doch meine Methoden umbenennen. Sonst verbau ich mir eine Menge Möglichkeiten. So'n Mist! |
Re: EntwZeit - Subkomponente löschen - Exception wird ausgel
Nachtrag:
Ich habe versucht ein Design-Pattern zu entwerfen, damit ich in die Komponente neue SubKomponenten einbinden kann, ohne jedesmal eine if-Anweisung in die Notification einzubauen, die explizit überprüft, ob Parameter-Komponente "pComponent" = private Komponente ist. Es wurde kein Design-Pattern, sondern ich habe nochmal die existierende If-Anweisung überarbeitet. @Philip Jetzt versteh ich, was Du eigentlich mit if-Anweisung überarbeiten meintest.
Delphi-Quellcode:
So, nun kann man alle möglichen Subkomponenten in die Komponente einbauen und diese im Obj.-Inspektor wieder löschen.
procedure TDkMailAccount.Notification
( pComponent : TComponent; pOperation : TOperation ); begin inherited Notification( pComponent, pOperation ); if pOperation = opRemove then pComponent := nil; end; |
Alle Zeitangaben in WEZ +1. Es ist jetzt 14:11 Uhr. |
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 by Thomas Breitkreuz