![]() |
Delphi-Version: XE2
Methoden-Deklaration vorgeben?
Ein weiterer absolut nichtssagender Titel. Bessere Vorschläge erbeten. Tags habe ich auch keine...
Nehmen wir an, ich bin im Begriff einen Batzen an Prozeduren zu deklarieren welche alle die gleiche Parameterliste haben. Anstatt nun jedes mal hinzugehen und zu sagen
Delphi-Quellcode:
Kann ich nicht einmal einen Typ deklarieren und dann immer sagen
type TMeineKlasse = class
procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc2(input1: Integer; input2: TSomeClass; out output: Double); [...]
Delphi-Quellcode:
Da ich so etwas bislang noch nicht gesehen habe ist die Hoffnung jetzt schon im Keller :(
type TMeineKlasse = class
type TProcType = procedure(input1: Integer; input2: TSomeClass; out output: Double) of object; procedure proc1 = TProcType; procedure proc2 = TProcType; [...] |
AW: Methoden-Deklaration vorgeben?
Dann schau dir mal die VCL Sourcen an :zwinker:
|
AW: Methoden-Deklaration vorgeben?
Ja die Eventhandler wie
Delphi-Quellcode:
sind mir auch als erstes eingefallen - Und gerade dort sehe ich so etwas nicht: Einmal gibt der TNotifyEvent-Typ die Parameterliste vor, dann beinhaltet die Deklaration jeder "onClick"-Methode wieder (redundant?) die Parameterliste in Form von "Sender: TObject".
TNotifyEvent
|
AW: Methoden-Deklaration vorgeben?
Zitat:
Nein, geht nicht. |
AW: Methoden-Deklaration vorgeben?
wat :|
|
AW: Methoden-Deklaration vorgeben?
Ich frage mich eher, ob es nicht eine bessere Lösung gibt. Das hört sich für mich eher wie eine Frage nach der Umsetzung einer ungünstigen Lösung des Problems an als nach einer Frage nach dem Problem selbst...
|
AW: Methoden-Deklaration vorgeben?
Nichts großartiges - Es ging um das Empfangen von Netzwerkpaketen und Erstellen einer Antwort. Je nachdem was für eine Information im ankommenden Paket enthalten ist, werden vollkommen unterschiedliche Dinge getan.
Delphi-Quellcode:
Die Methoden wie
if ankommendesPaket.commandStr = 'zooBesuch' then
TPaketbehandler.zooBesuchProc(ankommendesPaket, ausgehendesPaket, weitereParams) else if ankommendesPaket.commandStr = 'zirkusBesuch' then TPaketbehandler.zirkusBesuchProc(ankommendesPaket, ausgehendesPaket, weitereParams) ;
Delphi-Quellcode:
schauen sich das Paket an, tuen entsprechende Dinge und generieren eine Antwort. Mehr steckt nicht dahinter.
zooBesuchProc
Abgesehen davon welches halbe Dutzend etablierte Patterns ich hier hätte unterbringen können, rein syntaktisch wollte mir nur sparen, für alle Methoden ständig die gleichen Parameterlisten in der Deklaration runterzutippen sondern es einmal an einem Platz haben... |
AW: Methoden-Deklaration vorgeben?
Zitat:
Delphi-Quellcode:
Danach mußt du nur noch die Proceduren-Bezeichner der Kopien ändern:
private
procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc1(input1: Integer; input2: TSomeClass; out output: Double);
Delphi-Quellcode:
Am Schluß erzeugst du die Methoden mit Strg+Shift+C:
private
procedure proc1(input1: Integer; input2: TSomeClass; out output: Double); procedure proc2(input1: Integer; input2: TSomeClass; out output: Double); procedure proc3(input1: Integer; input2: TSomeClass; out output: Double); procedure proc4(input1: Integer; input2: TSomeClass; out output: Double); procedure proc5(input1: Integer; input2: TSomeClass; out output: Double); procedure proc6(input1: Integer; input2: TSomeClass; out output: Double); procedure proc7(input1: Integer; input2: TSomeClass; out output: Double);
Delphi-Quellcode:
Dauer der Aktion bei 7 Proceduren: Unter einer Minute!
procedure TForm1.proc1(input1: Integer; input2: TSomeClass; out output: Double);
begin end; procedure TForm1.proc2(input1: Integer; input2: TSomeClass; out output: Double); begin end; procedure TForm1.proc3(input1: Integer; input2: TSomeClass; out output: Double); begin end; procedure TForm1.proc4(input1: Integer; input2: TSomeClass; out output: Double); begin end; procedure TForm1.proc5(input1: Integer; input2: TSomeClass; out output: Double); begin end; procedure TForm1.proc6(input1: Integer; input2: TSomeClass; out output: Double); begin end; procedure TForm1.proc7(input1: Integer; input2: TSomeClass; out output: Double); begin end; |
AW: Methoden-Deklaration vorgeben?
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Richtig. So wie manche Bodybuilder auf Veranstaltungen gehen und ihren Körper bewundern lassen, führe ich oft vor, in welcher Geschwindigkeit meine Finger über die Tastatur huschen und mit welchen raffinierten RAD Studio-Tricks ich die wunderbarsten Dinge ermögliche. Ersteres könnte ich natürlich auch, aber da spielt Delphi nur noch eine untergeordnete Rolle.
Tipp des Tages: Die Code-Completion geht sogar rückwärts: Funktion direkt implementieren und der Editor ergänzt die Deklaration in der Klasse. Zitat:
Ich hätte die Parameterliste gerne nicht ein Dutzend mal redundant im Quelltext. Hat so etwas eigentlich einen hippen Fachbegriff? |
AW: Methoden-Deklaration vorgeben?
Zitat:
![]() Edit: Ich darf DRY nicht großschreiben. :-/ Edit2: ... oder nur, wenn ich ganze Sätze formuliere. :oops: |
AW: Methoden-Deklaration vorgeben?
Das kann man auch schön so umsetzen
Delphi-Quellcode:
Jetzt für jeden konkreten Befehl so eine Klasse erstellen und die jeweilige Instanz in einem
IMyMethod = interface
procedure Execute( input1: Integer; input2: TSomeClass; out output: Double ); end; // Eine Dummy-Klasse zum Veranschaulichen TMyDummyMethod = class( TInterfacedObject, IMyMethod ) protected procedure Execute( input1: Integer; input2: TSomeClass; out output: Double ); end; procedure TMyMethod.Execute( input1: Integer; input2: TSomeClass; out output: Double ); begin output := 0; end;
Delphi-Quellcode:
verwalten
TDictionary<string,IMyMethod>
Der Aufruf gestaltet sich ja dann sehr smart
Delphi-Quellcode:
Man kann das auch mit einem
type
TPacketHandler = class private fMethodDict : TDictionary<string,IMyMethod>; public procedure Execute( const ACommandStr : string; input1: Integer; input2: TSomeClass; out output: Double ); procedure AddMethod( const ACommandStr : string; AMethod : IMyMethod ); end; procedure TPacketHandler.Execute( const ACommandStr : string; input1: Integer; input2: TSomeClass; out output: Double ); begin fMethodDict[ACommandStr].Execute( input1, input2, output ); end; procedure TPacketHandler.AddMethod( const ACommandStr : string; AMethod : IMyMethod ); begin fMethodDict.AddOrSet( ACommandStr, AMethod ); end; ![]() |
AW: Methoden-Deklaration vorgeben?
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Zitat:
Mit Makros à la C++ würde es funktionieren:
Code:
Am schönsten fände ich es, wenn man einen vordefinierten Funktions-/Methodentyp bei der Deklaration benutzen könnte.
#define DECLARE_HANDLER_PROC(NAME) procedure NAME(input1: Integer; input2: TSomeClass; out output: Double)
DECLARE_HANDLER_PROC(proc1); DECLARE_HANDLER_PROC(proc2); DECLARE_HANDLER_PROC(proc3); DECLARE_HANDLER_PROC(proc4); DECLARE_HANDLER_PROC(proc5); Das habe ich aber noch in keiner Sprache gesehen. |
AW: Methoden-Deklaration vorgeben?
Zitat:
Also: Mach es wie Sir Rufo vorgeschlagen hat: Nimm eine Factory. |
AW: Methoden-Deklaration vorgeben?
Zitat:
"Wie teile ich Methoden auf Klassen auf." => Factories, usw. sondern: "Wie vermeide ich es, tausendmal (auch in verschiedenen Klassen) die gleiche Signatur zu tippen.". Gerade bei ![]() Oder übersehe ich da etwas? BTW: Meine "Lieblingslösung" wurde ja schon im Ausgangspost genannt :oops: |
AW: Methoden-Deklaration vorgeben?
@Sir Rufo, Furtbichler: Ändert allerdings auch nichts daran, dass man die Parameterdeklaration bei jeder Methode wieder hinschreiben muss.
Wenn dann würde sich vielleicht eher dieses Pattern anbieten, wo man statt die Parameter einzeln zu übergeben, ein einziges Objekt übergibt, das alle Parameter beinhaltet... mit Namen hab ichs nicht so :-D. So spielt die dann Reihenfolge keine Rolle und man kann auch neue Parameter hinzufügen, ohne alle Methoden anpassen zu müssen. Also statt:
Delphi-Quellcode:
TMyDummyMethod = class
protected procedure Execute( input1: Integer; input2: TSomeClass; out output: Double ); end; procedure TPacketHandler.Execute( const ACommandStr : string; input1: Integer; input2: TSomeClass; out output: Double ); begin fMethodDict[ACommandStr].Execute( input1, input2, output ); end;
Delphi-Quellcode:
(jaja public Felder sind pöhse usw., ist nur qualitativ).
TMyMethodParameters = class
input1: Integer; input2: TSomeClass; output: Double; end; TMyDummyMethod = class protected procedure Execute(parameters: TMyMethodParameters); end; procedure TPacketHandler.Execute( const ACommandStr : string; input1: Integer; input2: TSomeClass; out output: Double ); var Parameters: TMyMethodParameters; begin Parameters:= TMyMethodParameters.Create(input2, input2, output); fMethodDict[ACommandStr].Execute(Arguments); Parameters.Free; end; Aber KISS. |
AW: Methoden-Deklaration vorgeben?
Tippen an sich sollte man noch jedem zutrauen können :-D
Es sollte ja nicht darum gehen, weniger Tasten drücken zu müssen, sondern das ganze leichter wartbar zu machen und die Gelegenheit hier etwas falsch oder uneinheitlich zu machen zu entfernen. Wenn ich mittels Interface oder Oberklasse die Signatur schon vorgebe (wie z.B. bei Sir Rufo) erreiche ich das ja. Nur meiner Meinung nach für so klitzekleine Dinge wie in meinem Beispiel trotzdem etwas ... oversized. In zwei Jahren hat sich das ganze zwar garantiert dermaßen aufgebläht dass ich weinend am Boden liege und jammere "Warum habe ich nicht gleich auf ihn gehört", aber trotzdem :spin: |
AW: Methoden-Deklaration vorgeben?
Zitat:
Aber falsch ist die Vorgehensweise trotzdem. So. ;-) Bei VS bzw. Resharper geht das ganz einfach:
Code:
ALT-Enter, Enter, fertig (Refactoring "Implement Methods" wird ausgeführt). Gibts da was für Delphi?
class MyNewClass : IMyMethod{}
Zitat:
Gewöhne Dir das einfach an. Factories sind soooo praktisch und dir wird alle Nase lang etwas über den Weg laufen, wo Du anhand eines Tokens (String, Enum, sonstewas) eine Methode aufrufen musst. |
AW: Methoden-Deklaration vorgeben?
Zitat:
Zitat:
|
AW: Methoden-Deklaration vorgeben?
Zitat:
Klassendeklaration hinschreiben inkl. end, vor dem end bleiben, Strg + Leertaste, zu implementierende Methoden des Interfaces aus der Liste auswählen, Enter (jetzt stehen sie da inkl. public), Strg + Shift + C, fertig. ;-) |
AW: Methoden-Deklaration vorgeben?
@jaenicke :thumb:
Obwohl mich das
Delphi-Quellcode:
eher stört, das verleitet einige statt dem Interface, die Klassen-Instanz zu benutzen.
public
Also definiere ich die Klassen entweder im
Delphi-Quellcode:
-Abschnitt (Zugriff dann über eine Factory) oder deklariere diese Methoden als
implementation
Delphi-Quellcode:
.
protected
|
AW: Methoden-Deklaration vorgeben?
Mit geschachtelten Funktionen lässt sich das "Problem" lösen:
Delphi-Quellcode:
procedure AllInOneHandler(input1: Integer; input2: TSomeClass; out output: Double);
procedure proc1; // hat Zugriff auf die Parameter der äusseren Funktion oder Methode begin end; procedure proc2; // so was von dry - dryer geht's nicht begin end; begin if ankommendesPaket.commandStr = 'zooBesuch' then proc1 else if ankommendesPaket.commandStr = 'zirkusBesuch' then proc2 else ... end; |
AW: Methoden-Deklaration vorgeben?
Zitat:
Das Interface deklarierst du ja hoffentlich nicht in der selben Unit wie das Objekt, oder? Wer dann die Unit mit dem Objekt extra nimmt, ist selbst schuld... Nebenbei kann man bei XE4 anders als früher auch problemlos den Interface-Zeiger wieder auf die Objektinstanz casten (mit as). Auch noch nebenbei: Das Überschreiben von Elternmethoden funktioniert analog inkl. override dahinter. ;-) Das public wieder zu entfernen ist jedenfalls deutlich weniger Arbeit als alles manuell zu kopieren usw. ;-) |
AW: Methoden-Deklaration vorgeben?
Zitat:
Zitat:
Interface-Methoden sollten public sein, schließlich verwendet man sie ja 'öffentlich', auch wenn die Klasse an sich nicht verfügbar sein sollte. |
AW: Methoden-Deklaration vorgeben?
Zitat:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 13:10 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