Ohne Nil prüfen ob Objekt erstellt wurde.
Ohne Nil prüfen ob Objekt erstellt wurde.
Gibt es eigentlich (neuerdings) eine Möglichkeit, so etwas wie "if Assigned()" zu machen, ohne dass man die Objektvariable vorher auf Nil setzt und ohne ein SIGSEGV abzufangen?
Bei Records kann man ja leider nicht von Nil, 0 etc ausgehen.
Bei Records kann man ja leider nicht von Nil, 0 etc ausgehen.
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Soviel ich weiß, werden nur globale Instanzen mit Nil vorbelegt.
Code: Alles auswählen
type
TLiveSelection = (lsMoney, lsChilds, lsTime);
TLive = Array[0..1] of TLiveSelection;
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Michl hat geschrieben:Soviel ich weiß, werden nur globale Instanzen mit Nil vorbelegt.
Ja, das ist klar. Wie prüfe ich also in diesem Falle, ob ein Objekt schon erstellt ist?
-
- Beiträge: 1910
- Registriert: Di 23. Sep 2014, 17:46
- OS, Lazarus, FPC: Win10 | Linux
- CPU-Target: x86_64
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Gar nicht, nicht mal eine seg fault ist garantiert, wenn später etwas anderes im Speicher steht kann an dieser Stelle auf die die Variable zeigt kann Gott weiß was passieren (z.b. ein zweites Objekt der selben klasse wird an der Stelle initialisiert, dann ist der Zeiger valide, obwohl du das so nie wolltest).
Die Zeiger musst du eben selbst mit Nil initialisieren
Ein Beispiel:
Resultat ist B, da der selbe Speicherbereich wieder verwendet wurde
Über einen Zeiger der nicht auf Nil steht kann man keine Aussage treffen
Die Zeiger musst du eben selbst mit Nil initialisieren
Ein Beispiel:
Code: Alles auswählen
procedure TForm1.Button1Click(Sender: TObject);
var sl, sl2: TStringList;
begin
sl:=TStringList.Create;
sl.Text:='A';
sl.Free;
sl2:=TStringList.Create;
sl2.Text:='B';
ShowMessage(sl.Text);
end;
Resultat ist B, da der selbe Speicherbereich wieder verwendet wurde
Über einen Zeiger der nicht auf Nil steht kann man keine Aussage treffen
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Warf hat geschrieben:Die Zeiger musst du eben selbst mit Nil initialisieren
Das geht aber nicht. In einem (Advanced) Record habe ich afaik kein Create oder sowas.
Ich muss das Objekt erstellen, in dem Moment wo es angefordert wird und da habe ich also keine Chance zu erkennen, ob es schon da ist, außer über eine abgefangene Exception, was hässlich wäre.
-
- Beiträge: 1910
- Registriert: Di 23. Sep 2014, 17:46
- OS, Lazarus, FPC: Win10 | Linux
- CPU-Target: x86_64
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Du könntest deine Records in einer separaten Datei mit Mode Delphi auslagern, dann dürfte es möglich sein konstruktoren zu verwenden
Und das mit der exception ist auch nicht sicher, siehe Beispiel oben
Und das mit der exception ist auch nicht sicher, siehe Beispiel oben
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Warf hat geschrieben:Du könntest deine Records in einer separaten Datei mit Mode Delphi auslagern, dann dürfte es möglich sein konstruktoren zu verwenden
Was meinst du damit?
-
- Beiträge: 1910
- Registriert: Di 23. Sep 2014, 17:46
- OS, Lazarus, FPC: Win10 | Linux
- CPU-Target: x86_64
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Eine Separate Unit für die Record definition, bei dieser Unit setzt du den Compilerswitch {$MODE Delphi} und kannst dort dann einen Konstruktor für den Record schreiben
Dann zum benutzen einfach diese Unit einbinden, und du hast einen Record mit Konstruktor so wie in Delphi
PS: habe ich nicht getestet, ist nur eine Vermutung dass es so geht
Code: Alles auswählen
unit TestRecord;
{$MODE Delphi}
interface
type
TTestRec = record
...
constructor Create;
end;
implementation
constructor TTestRec.Create;
begin
...
end;
end.
Dann zum benutzen einfach diese Unit einbinden, und du hast einen Record mit Konstruktor so wie in Delphi
PS: habe ich nicht getestet, ist nur eine Vermutung dass es so geht
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Ich habe das auch nicht getestet.
Aber es macht für mich auch keine Sinn. Wenn ich "Createn" wollte, würde ich eine Klasse bauen und keinen Record.
Andere aber ähnliche Frage: Kann man eine Interfacevariable irgendwie darauf testen, ob sie "gebrauchsfertig" ist?
Aber es macht für mich auch keine Sinn. Wenn ich "Createn" wollte, würde ich eine Klasse bauen und keinen Record.
Andere aber ähnliche Frage: Kann man eine Interfacevariable irgendwie darauf testen, ob sie "gebrauchsfertig" ist?
Code: Alles auswählen
type
ITestInterface = interface
procedure DoSomething;
end;
var
I: ITestInterface;
begin
....
BinIchCreated(I);
-
- Beiträge: 309
- Registriert: Sa 21. Mär 2009, 17:31
- OS, Lazarus, FPC: Linux (Lazarus SVN, FPC 2.4)
- CPU-Target: 64 Bit
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
theo hat geschrieben:Andere aber ähnliche Frage: Kann man eine Interfacevariable irgendwie darauf testen, ob sie "gebrauchsfertig" ist?
assigned(i) ?
Die werden wohl automatisch auf nil gesetzt
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
BeniBela hat geschrieben:assigned(i) ?
Die werden wohl automatisch auf nil gesetzt
Nein, werden sie nicht. Siehe oben.
Naja egal. Geht wohl einfach nicht.
-
- Lazarusforum e. V.
- Beiträge: 3158
- Registriert: Di 22. Jul 2008, 19:27
- OS, Lazarus, FPC: Lazarus: SVN; FPC: svn; Win 10/Linux/Raspbian/openSUSE
- CPU-Target: 32bit x86 armhf
- Wohnort: Köln
- Kontaktdaten:
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
theo hat geschrieben:BeniBela hat geschrieben:assigned(i) ?
Die werden wohl automatisch auf nil gesetzt
Nein, werden sie nicht. Siehe oben.
Naja egal. Geht wohl einfach nicht.
Dann setz die Variable doch auf nil, sobald sie verfügbar ist!
MfG Socke
Ein Gedicht braucht keinen Reim//Ich pack’ hier trotzdem einen rein
Ein Gedicht braucht keinen Reim//Ich pack’ hier trotzdem einen rein
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Socke hat geschrieben:theo hat geschrieben:BeniBela hat geschrieben:assigned(i) ?
Die werden wohl automatisch auf nil gesetzt
Nein, werden sie nicht. Siehe oben.
Naja egal. Geht wohl einfach nicht.
Dann setz die Variable doch auf nil, sobald sie verfügbar ist!
Und wann wäre das innerhalb eines Records?
-
- Beiträge: 309
- Registriert: Sa 21. Mär 2009, 17:31
- OS, Lazarus, FPC: Linux (Lazarus SVN, FPC 2.4)
- CPU-Target: 64 Bit
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
theo hat geschrieben:Nein, werden sie nicht. Siehe oben./quote]
Hängt wohl davon ab, wo der record herkommt
Zumindest bei Stackrecords habe ich immer nil erhalten
GetMem ist wohl anders
[/quote]Socke hat geschrieben:Dann setz die Variable doch auf nil, sobald sie verfügbar ist!
Aber mit FillChar
Wenn man einer nicht initialisierten Interfacevariable mit := nil zuweist, ruft es deref auf und stürzt ab
Re: Ohne Nil prüfen ob Objekt erstellt wurde.
Nochmal.
Die Situation wäre verkürzt so:
Jetzt möchte ich TuWasMitdemInterface aufrufen, und diese soll das fMyIntf createn, aber nur beim ersten Mal.
Das geht nicht, weil ich nicht prüfen kann, ob das fMyIntf schon created wurde, da fMyIntf anfänglich nicht Nil ist und es auch kein Event gibt, dies selber zu "nillen".
Es geht nicht. Ist OK.
Die Situation wäre verkürzt so:
Code: Alles auswählen
{$MODESWITCH ADVANCEDRECORDS}
...
TMyRec=Record
private
fMyIntf: IIrgendWas;
public
procedure TuWasMitdemInterface;
end;
Jetzt möchte ich TuWasMitdemInterface aufrufen, und diese soll das fMyIntf createn, aber nur beim ersten Mal.
Das geht nicht, weil ich nicht prüfen kann, ob das fMyIntf schon created wurde, da fMyIntf anfänglich nicht Nil ist und es auch kein Event gibt, dies selber zu "nillen".
Es geht nicht. Ist OK.