AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Thema durchsuchen
Ansicht
Themen-Optionen

pchar freigeben?

Ein Thema von mumu · begonnen am 15. Feb 2006 · letzter Beitrag vom 16. Feb 2006
Antwort Antwort
Seite 2 von 3     12 3      
mumu

Registriert seit: 28. Okt 2003
Ort: Bamberg
519 Beiträge
 
#11

Re: pchar freigeben?

  Alt 16. Feb 2006, 08:08
Zitat von mumu:
vielen vielen dank für die ausführliche antwort !!!!

aber eine frage hätte ich noch:
Delphi-Quellcode:
p_char: PChar;
begin
...
  p_char := nil;
  FreeMem(p_char);
end;
macht sowas sinn? wenn ich doch den p_char auf nil setz, dann kann ich doch den speichernbereich mit FreeMem nicht mehr freigeben, weil ich ja net weiß, wohin der p_char zeigt, oder?

// edit:
ahh hier steht ja die antwort, sorry
Zitat:
Die Variable lediglich auf den Wert nil zu setzen ist sinnlos. Wenn ich den Speicher noch nicht freigegeben habe, verliere ich damit die Referenz auf den Speicher (der somit allokiert bleibt). Wenn ich den Speicher bereits freigegeben habe, benötige ich eine Zuweisung auf nil nicht mehr.
Da man PChars in der Regel auch zum Referenzieren von Speicherblöcken benutzt und nicht, weil sie bei den Variablen-Definitionen schick aussehen, muss man diese Speicherblöcke auch wieder freigeben.
aber trotzdem nochmal die frage, damit ich mir auch 100 prozentig sicher bin:
folgendes in der reihenfolge kann eigentlich nie sinn machen, oder?
p_char := nil;
FreeMem(p_char);

weil ich schnall irgendwie net, warum mein vorgänger, dass bei jedem p_char gemacht hat?! Ich würd auf sowas eigentlich schon gar nicht kommen?!
  Mit Zitat antworten Zitat
Benutzerbild von Luckie
Luckie

Registriert seit: 29. Mai 2002
37.621 Beiträge
 
Delphi 2006 Professional
 
#12

Re: pchar freigeben?

  Alt 16. Feb 2006, 08:09
Dein Code wird eine AV auslösen, weil, wie Thomas erklärt hat, mit nil die Referenz gelöscht wird, aber das wird sie sowieso nach verlassen der lokalen Routine. Allein das FreeMem ist wichtig, wenn du Speicher mit GetMem reervierst, um den Speicher wieder frezugeben und aufzuräumen.
Michael
Ein Teil meines Codes würde euch verunsichern.
  Mit Zitat antworten Zitat
mumu

Registriert seit: 28. Okt 2003
Ort: Bamberg
519 Beiträge
 
#13

Re: pchar freigeben?

  Alt 16. Feb 2006, 08:30
hi luckie,

nee eben nicht, da werden keine av's ausgelöst. das ist ja eben das komische?! und der verwendet des wirklich überall im code???
  Mit Zitat antworten Zitat
Muetze1
(Gast)

n/a Beiträge
 
#14

Re: pchar freigeben?

  Alt 16. Feb 2006, 09:21
Ja, weil FreeMem() intelligent ist und einen NULL/NIL Parameter handeln kann - sprich: ihn ignoriert. Das geht gehört mit dem Funktionssyntax AllocMem() ReAllocMem(), wobei letztere auch Speicher freigeben und den Zeiger bei einer Grösse von 0 auf Nil setzen. Trotzdem kann bei Verwendung eines solchen Codes immer FreeMem() am Ende aufgerufen werden, damit bei eventuell nicht auf eine Grösse von 0 reduzierte Bereiche freigegeben werden.
  Mit Zitat antworten Zitat
mumu

Registriert seit: 28. Okt 2003
Ort: Bamberg
519 Beiträge
 
#15

Re: pchar freigeben?

  Alt 16. Feb 2006, 09:41
Zitat:
Trotzdem kann bei Verwendung eines solchen Codes immer FreeMem() am Ende aufgerufen werden, damit bei eventuell nicht auf eine Grösse von 0 reduzierte Bereiche freigegeben werden.
hä? woher will der wissen, welche bereiche freigegeben werden müssen, wenn er ja nur nil übergeben bekommt?

wenn ich aber jetzt alles von
Delphi-Quellcode:
p_char: PChar;
begin
...
  p_char := nil;
  FreeMem(p_char);
end;
in

Delphi-Quellcode:
p_char: PChar;
begin
...
  FreeMem(p_char);
end;
ändere, dann sollte es eigentlich keine probleme geben, oder?
  Mit Zitat antworten Zitat
Muetze1
(Gast)

n/a Beiträge
 
#16

Re: pchar freigeben?

  Alt 16. Feb 2006, 09:53
Zitat von mumu:
Zitat:
Trotzdem kann bei Verwendung eines solchen Codes immer FreeMem() am Ende aufgerufen werden, damit bei eventuell nicht auf eine Grösse von 0 reduzierte Bereiche freigegeben werden.
hä? woher will der wissen, welche bereiche freigegeben werden müssen, wenn er ja nur nil übergeben bekommt?
Wenn er NIL bekommt ist nix mehr freizugeben. Ist der übergebene Zeiger noch <> NIL, dann ist noch was freizugeben. Was ist daran denn so unverständlich?

Zitat von mumu:
wenn ich aber jetzt alles von
Delphi-Quellcode:
p_char: PChar;
begin
...
  p_char := nil;
  FreeMem(p_char);
end;
in

Delphi-Quellcode:
p_char: PChar;
begin
...
  FreeMem(p_char);
end;
ändere, dann sollte es eigentlich keine probleme geben, oder?
Ich weiss nicht wie du bei den "..." Bereich im Code den PChar belegst, aber von dem reinen hier zu sehenden Code bekommst du dadurch höchstwahrscheinlich AV's, da der PChar zufällige Werte enthält (da lokale Variable).
  Mit Zitat antworten Zitat
tommie-lie
(Gast)

n/a Beiträge
 
#17

Re: pchar freigeben?

  Alt 16. Feb 2006, 11:33
Zitat von Muetze1:
Ich weiss nicht wie du bei den "..." Bereich im Code den PChar belegst, aber von dem reinen hier zu sehenden Code bekommst du dadurch höchstwahrscheinlich AV's, da der PChar zufällige Werte enthält (da lokale Variable).
Wie ich oben schon schrob ist eigentlich davon auszuegehen, daß PChar-Variablen auch verwendet werden und nicht nur existieren, weil sie schön aussehen. Es gibt Ausnahmen (eine davon war oben von mir benanntes Pascal-String-Beispiel), aber in der Regel sollte man schon ein FreeMem() oder Dispose() auf den PChar durchführen.
Kurzum, um folgende Frage zu beantworten:
Zitat von mumu:
woher will der wissen, welche bereiche freigegeben werden müssen, wenn er ja nur nil übergeben bekommt?
Kann er nicht, und genau das ist das Problem. Wenn FreeMem() einen Zeiger auf nil übergeben bekommt, passiert exakt "gar nichts". Wenn du einen gültigen Pointer auf nil setzt, weißt du anschließend nicht mehr, wo genau im Speicher der dazugehörige Speicherblock zeigt, du hast ja soeben deinen einzigen Zeiger auf diesen Block mit nil gefüllt. FreeMem() kann auch nicht hellsehen, es kann diesen "verwaisten" Speicherbereich auch nicht mehr finden und freigeben. Somit bleibt der Speicherbereich allokiert bis zum StNimmerleinstag, oder bis das Programm beendet wird und Windows den gesamten Adressbereich des Prozesses freigibt.

Zu deiner nil-Geschichte:
Vielleicht ist dir in einigen Quellcodes schon aufgefallen, daß Objekte nicht mit objekt.Free() freigegeben werden, sondern mit FreeAndNil(objekt). Free() setzt, ebenso wie FreeMem() den Pointer *nicht* auf nil, sondern lässt ihn auf dem alten Wert (irgendwo im Speicher) und gibt lediglich den freigegebenen Speicher frei. Da mit FreeAndNil() meine Objektreferenz nil wird, kann ich zu einem späteren Zeitpunkt feststellen, ob mein Objekt freigegeben ist bzw ob ich mit meiner Objektreferenz tatsächlich noch ein existierendes Objekt habe. Genauso kann man es mit PChars machen. Erst freigeben und nachher selber af nil setzen (und nur in dieser Reihenfolge!). Dann kannst du später mit einer if-Abfrage überprüfen ob der PChar noch gültig ist. Wenn du das in deinem gesamten Programm konsequent durchziehst, kann man pauschal die Aussage treffen: Alle PChars, die nicht nil sind, verweisen auf einen gültigen Speicherbereich. Solche Aussagen können sich irgendwann mal als praktisch erweisen.

Zitat von mumu:
weil ich schnall irgendwie net, warum mein vorgänger, dass bei jedem p_char gemacht hat?!
Vielleicht Unwissen - wohl der Grund, warum er jetzt nur Vorgänger ist
Es ist in dieser Reihenfolge jedenfalls falsch und unsinnig.
  Mit Zitat antworten Zitat
mumu

Registriert seit: 28. Okt 2003
Ort: Bamberg
519 Beiträge
 
#18

Re: pchar freigeben?

  Alt 16. Feb 2006, 11:41
Zitat:
ich weiss nicht wie du bei den "..." Bereich im Code den PChar belegst, aber von dem reinen hier zu sehenden Code bekommst du dadurch höchstwahrscheinlich AV's, da der PChar zufällige Werte enthält (da lokale Variable).
ja es ist schon klar, natürlich wird davor mit GetMem Speicher angefordert.

Vielen vielen Dank Tommie-lie genau auf so eine klipp und klare antwort habe ich gehofft
  Mit Zitat antworten Zitat
Muetze1
(Gast)

n/a Beiträge
 
#19

Re: pchar freigeben?

  Alt 16. Feb 2006, 14:37
Zitat von tommie-lie:
Dann kannst du später mit einer if-Abfrage überprüfen ob der PChar noch gültig ist. Wenn du das in deinem gesamten Programm konsequent durchziehst, kann man pauschal die Aussage treffen: Alle PChars, die nicht nil sind, verweisen auf einen gültigen Speicherbereich. Solche Aussagen können sich irgendwann mal als praktisch erweisen.
Man sollte vllt. in dem Sinne noch darauf hinweisen, wenn ein lokaler AnsiString mit einem Typecast zu einem PChar gewandelt wird, weil dann wird der PChar mit verlassen der Procedure ungültig (mit dem AnsiString, auf den er halt zeigt). Dies ist in dem Falle zu beachten, dann kann man beim konsequenten zurücksetzen von deiner Aussage ausgehen. (PChar als Funktionsergebnis, etc)

Zitat von mumu:
ja es ist schon klar, natürlich wird davor mit GetMem Speicher angefordert.
Da es aber viele Möglichkeiten gibt und es auch andere Speicherreservierungen als GetMem() gibt, ist nicht immer FreeMem() richtig, daher habe ich mich nicht zu der grundlegenden Aussage hinreissen lassen, dass FreeMem() richtig ist. Hättest du GetMem() in dem Kurz-Pseudo-Code mit hingeschrieben, hätte ich das bestätigt.

Man muss halt genau sein, sonst heisst es ein halbes Jahr später wieder: "Aber du hattest doch geschrieben ..." und man stellt mit Entsetzen fest, es war nicht eindeutig formuliert bzw. derjenige denkt nicht an das an was ich damals dachte...
  Mit Zitat antworten Zitat
Benutzerbild von Flocke
Flocke

Registriert seit: 9. Jun 2005
Ort: Unna
1.172 Beiträge
 
Delphi 10.2 Tokyo Professional
 
#20

Re: pchar freigeben?

  Alt 16. Feb 2006, 15:43
Wenn du den Speicher selbst mit GetMem holst, und wenn du es `ganz´ sauber machen willst, dann schreibe es so:

Delphi-Quellcode:
var
  p_char: PChar;
begin
  ...
  GetMem(p_char, n_char);
  try
    ...
  finally
    FreeMem(p_char);
  end;
end;
Volker
Besucht meine Garage
Aktuell: RtfLabel 1.3d, PrintToFile 1.4
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 2 von 3     12 3      


Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 16:39 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