![]() |
Re: Record zurücksetzen (löschen)
Zitat:
|
Re: Record zurücksetzen (löschen)
Mh nee.. Ich glaube das siehst du richtig. Jetzt wo du's sagst... Muss man halt wirklich ne Record-Methode (seltsame Teile wie ich finde..) schreiben
Zitat:
|
Re: Record zurücksetzen (löschen)
@Michael:
Danke für das "Entschrummpeln" der Forumsansicht! :thumb: Zitat:
Zitat:
Was ich vorhabe: Zum einen will ich hierbei meinen Delphi-Horizont erweitern. Bisher habe ich bei Records eine Routine geschrieben, in der alle Felder auf einen definierten Wert gesetzt wurden. Beispiel:
Delphi-Quellcode:
Nun will ich zum Einen wissen, ob es da eine einfachere Möglichkeiten gibt, um meinen Code kürzer und übersichtlicher zu halten.Type TMyRecord = record Test_1 : string; Test_2 : string; Integer_1 : Integer; Integer_2 : Integer; end; function PrepareMsg(AMyRecord: TMyRecord): string; begin Result := 'Test_1: ' + AMyRecord.Test_1 + #13#10+ 'Test_2: ' + AMyRecord.Test_2 + #13#10+ 'Integer_1: ' + IntToStr(AMyRecord.Integer_1) + #13#10+ 'Integer_2: ' + IntToStr(AMyRecord.Integer_2); end; procedure ResetMyRecord(var AMyRecord: TMyRecord); begin AMyRecord.Test_1 := ''; AMyRecord.Test_2 := ''; AMyRecord.Integer_1 := 0; AMyRecord.Integer_2 := 0; end; procedure SetTestValues(var AMyRecord: TMyRecord); begin AMyRecord.Test_1 := 'Hallo '; AMyRecord.Test_2 := 'Welt!'; AMyRecord.Integer_1 := 9; AMyRecord.Integer_2 := 2008; end; procedure TForm1.Button1Click(Sender: TObject); var MyRecord: TMyRecord; begin // undefinierte AnfangsWerte (beim ersten Test erscheinen hier Zufallswerte) ShowMessage(PrepareMsg(MyRecord)); // BeispielWerte zuweisen SetTestValues(MyRecord); ShowMessage(PrepareMsg(MyRecord)); // mit "händischer" Lösung auf definierte AnfangsWerte setzen ResetMyRecord(MyRecord); ShowMessage(PrepareMsg(MyRecord)); // BeispielWerte zuweisen SetTestValues(MyRecord); ShowMessage(PrepareMsg(MyRecord)); // "FillChar"-Lösung Finalize(MyRecord); FillChar(MyRecord, SizeOf(MyRecord), 0); ShowMessage(PrepareMsg(MyRecord)); end; Zum Anderen hat die obige "händische" Lösung zwar den Vorteil, dass man selbst definierte Werte erhält, aber den Nachteil, dass das bei umfangreicheren Records schnell recht aufwendig wird. Hinzu kommt, dass in meinem konkretten Fall (Verknüpfungen auslesen) mein Record auch noch einen weiteren Record enthält. Da ist dann die Frage, wie weit die händische Lösung sinnvoll ist.
Delphi-Quellcode:
type
TMyRecord = record Test_1 : string; Test_2 : string; Integer_1 : Integer; Integer_2 : Integer; FindData: TWIN32FINDDATA; // <-- weiterer Record in meinem Record end; @toms Die "MyBlankRecord"-Lösung entspricht in meiner Auffassung der "händischen" Lösung, ist hier also nicht gewollt. Die "FillChar"-Lösung erscheint mir eher als eine Lösung in meinem Sinne. Gewünscht ist eine Lösung mit kurzem Code, die schon-vorhandene Delphi Routinen benutzt. Und das wäre hierbei der Fall. Und es schein sogar recht elegant zu sein. OK, nach ersten Tests (siehe Komplett-Code oben) scheint die "FillChar"-Möglichkeit tatsächlich die gewünschte "elegange" Lösung zu sein. Ich werde nun noch Test mit dem zusätzlichen Record in meinem Record (FindDate: TWIN32FINDDATA) durchführen. @Ronny Meines Wissens nach werden mit FillChar auch die Strings auf "0" gesetzt (komplett mit Nullen gefüllt, also sozusagen Null-terminiert). Das entspricht einem leeren String und ist das gewünschte Ziel. Mal sehen, was die anderen sagen. :-D Guido. |
Re: Record zurücksetzen (löschen)
Hi,
Ein "Beweis", dass FillChar nicht funktioniert:
Delphi-Quellcode:
Dürfte dann übrigens ein schönes Speicherleck geben ;) (Außer der Memory-Manager räumt das trotzdem auf)
type
TBeweis = packed record EinString: String; Zahl: Integer; end; var Beweis: TBeweis; p: Pointer; begin Beweis.EinString:= 'Test'; p := @Beweis.EinString[1]; FillChar(Beweis,SizeOf(TBeweis),0); ShowMessage(PChar(p)); end; Wie SubData schon gesagt hat: Der Pointer zu dem eigentlichen String wird auf nil gesetzt. Aber der String selbst schwirrt noch im Speicher rum. Ist nur nichtmehr erreichbar, falls man den Pointer nicht vorher gesichert hat ;) |
Re: Record zurücksetzen (löschen)
Liste der Anhänge anzeigen (Anzahl: 1)
Du beweist, dass man jedes noch so simple Problemchen derart verunstalten kann, dass es eventuell nicht mal richtig funktioniert. :mrgreen:
Delphi-Quellcode:
Das ergibt das im Anhang.
MyRecord.nr := 1;
MyRecord.name := 'XYZ'; memo2.Lines.Add(IntToStr(MyRecord.nr)); memo2.Lines.Add('*'+MyRecord.name+'*'); memo2.Lines.Add(''); FillChar (MyRecord,SizeOf (MyRecord),0); memo2.Lines.Add(IntToStr(MyRecord.nr)); memo2.Lines.Add('*'+MyRecord.name+'*'); |
Re: Record zurücksetzen (löschen)
Jap, so in etwa dachte ich mir das.
Finalize scheint aber auch nicht zu funktionieren. Jedenfalls nicht, wenn das Record eine ThreadVar ist. Zumindest meldet FastMM danach noch Speicherlecks. Edit: Zitat:
Ob der String damit aber wirklich freigegeben wurde, wird daraus nicht deutlich. |
Re: Record zurücksetzen (löschen)
Edit: Kann weg...
|
Re: Record zurücksetzen (löschen)
Natürlich steht dann in MyRecord.Name nichts mehr. Weil der String "genilt" wurde. Aber der String selbst liegt immernoch im Speicher rum.
|
Re: Record zurücksetzen (löschen)
Und ich wette FastMM würde rumnörgeln ;-)
Edit: Michael: Magste das mal mit FastMM testen? |
Re: Record zurücksetzen (löschen)
Zitat:
|
Alle Zeitangaben in WEZ +1. Es ist jetzt 03:00 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-2025 by Thomas Breitkreuz