Speicher freigeben

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut
zummy
Beiträge: 17
Registriert: Mo 6. Nov 2006, 14:00

Speicher freigeben

Beitrag von zummy »

Hallo Leute,

ich habe ein Problem mit der Speicherfreigabe:

Code: Alles auswählen

var primz: array of boolean;
...
setlength(primz, 1000000000);
... //rechne mit primz rum
setlength(primz,0);
Jedoch wird der Speicher, den primz belegt, nicht wieder freigegeben, wie man im Windows-Taskmanager sehen kann.

Auch Versuche wie

Code: Alles auswählen

primz.free;
helfen nicht.

Wie kann ich den Speicher freigeben, ohne die Applikation zu beenden?

Danke schonmal
Zummy

Christian
Beiträge: 6079
Registriert: Do 21. Sep 2006, 07:51
OS, Lazarus, FPC: iWinux (L 1.x.xy FPC 2.y.z)
CPU-Target: AVR,ARM,x86(-64)
Wohnort: Dessau
Kontaktdaten:

Beitrag von Christian »

Du machst das schon ganz richtig, SetLength(***,0); sollte den speicher freigeben schreib das doch mal an die fpc mailingliste.
W.m.k.A.h.e.m.F.h. -> http://www.gidf.de/

iaby
Beiträge: 24
Registriert: Mi 25. Okt 2006, 19:48

Beitrag von iaby »

das ist beim original-Delphi von Borland genauso!
Ist ein sehr hässliches Phänomen, weiß auch nicht wieso das passiert!

Quit
Beiträge: 65
Registriert: So 5. Nov 2006, 18:58
OS, Lazarus, FPC: Winux (L 0.9.xy FPC 2.2.z)
CPU-Target: xxBit
Wohnort: Luzern

Beitrag von Quit »

Und wenn du das nun auf zB 1 setzst?

iaby
Beiträge: 24
Registriert: Mi 25. Okt 2006, 19:48

Beitrag von iaby »

das hilft alles nichts. Wenn du z.B das Array nach und nach um 1 vergrößerst hast du nachher einen großen Brocken an reserviertem Speicher, den du so nicht mehr losbekommst!

Quit
Beiträge: 65
Registriert: So 5. Nov 2006, 18:58
OS, Lazarus, FPC: Winux (L 0.9.xy FPC 2.2.z)
CPU-Target: xxBit
Wohnort: Luzern

Beitrag von Quit »

Hm, mit dem Problem habe ich mich gar nicht auseinandergesetzt.
Wie löst man das am besten? Programm neustarten?

iaby
Beiträge: 24
Registriert: Mi 25. Okt 2006, 19:48

Beitrag von iaby »

am besten nich so oft die größe ändern!
Also mal viel speicher holen, dann die sachen da rein schreiben und bei bedarf wieder neuen anfordern, also je nach anwendung vielleicht platz für +1000 Einträge je SetLength.
Neustart der anwendung hilft natürlich auch!

Christian
Beiträge: 6079
Registriert: Do 21. Sep 2006, 07:51
OS, Lazarus, FPC: iWinux (L 1.x.xy FPC 2.y.z)
CPU-Target: AVR,ARM,x86(-64)
Wohnort: Dessau
Kontaktdaten:

Beitrag von Christian »

schreib doch einfach mal an die fpc liste ich kann mir ehrlich gesagt net vorstellen, das bei setlength(*,0) der Speciehr nicht wieder freigegeben wird.
hast du das nur mit dem taskmanager ausgelotet ?

Compilier doch mal die heaptrc unit mit ein,l die sagt dir genau wo speicherleaks sind. Einfach in den Projekt->Compilereinstellungen->Linker mal mit anhaken.
W.m.k.A.h.e.m.F.h. -> http://www.gidf.de/

Benutzeravatar
theo
Beiträge: 10856
Registriert: Mo 11. Sep 2006, 19:01

Beitrag von theo »

Bin nicht sicher ob's was hilft, aber probier doch mal

Code: Alles auswählen

Finalize(primz);

zummy
Beiträge: 17
Registriert: Mo 6. Nov 2006, 14:00

Beitrag von zummy »

Hi Leute,

danke für die vielen und schnellen Antworten!
Leider habe ich noch keine Lösung.

setlength(*,0) und setlength(*,1) helfen nicht.

Code: Alles auswählen

finalize(primz);
zeigt auch keinerlei Wirkung.

Und

Code: Alles auswählen

primz.free;
will er gar nicht erst komplieren (Error: illegal qualifier).

Sobald die Prozedur, die dem Array die Länge 1000000000 zuweist, gestartet wird, steigt die Speicheranzeige für den Prozess im Taskmanager auf über 900 MB und verbleibt auch dort, bis das Programm geschlossen ist. :(

Christian
Beiträge: 6079
Registriert: Do 21. Sep 2006, 07:51
OS, Lazarus, FPC: iWinux (L 1.x.xy FPC 2.y.z)
CPU-Target: AVR,ARM,x86(-64)
Wohnort: Dessau
Kontaktdaten:

Beitrag von Christian »

Wie in meinem ersten Posting gesagt, schreib an die Mailingliste denn du machst es schon richtig.
Prinz.Free
Primz ist ne Variable und kein Objekt wenn Wirth tot wär würd er sich im Grab umdrehn. Selbiges gilt für finalize ;) :p
warscheinlich sein Gesichtsausdruck wenn er das liest lol http://de.wikipedia.org/wiki/Bild:Nikla ... C_UrGU.jpg
W.m.k.A.h.e.m.F.h. -> http://www.gidf.de/

Benutzeravatar
theo
Beiträge: 10856
Registriert: Mo 11. Sep 2006, 19:01

Beitrag von theo »

Na na Christian.
Primz ist ein Dynamisches Array und wird durchaus mit Finalize oder Nil freigegeben. Es wird auch automatisch freigegeben, wenn keine Referenz mehr daruf besteht.
Ausserdem hat Wirth's Pascal mit ObjectPascal nicht viel am Hut.
Das wäre dann Modula2 oder Oberon,

Christian
Beiträge: 6079
Registriert: Do 21. Sep 2006, 07:51
OS, Lazarus, FPC: iWinux (L 1.x.xy FPC 2.y.z)
CPU-Target: AVR,ARM,x86(-64)
Wohnort: Dessau
Kontaktdaten:

Beitrag von Christian »

Stimmt dynamische arrays gabs zu seinen zeiten noch nicht.
Sie sind aber an die normalen arrays angelehnt, und deren Syntax stammt vom Wirth. Und auch dynamische arrays sind "nur" Variablen hat also mit Objekt Pascal aus sicht des Benutzers nichts zu tun (wie das intern gehandelt wird weiss ich net glaub aber auch nicht das dazu objekte benutzt werden).

Mit finalize hab ich mich vertan, das sollte wirklich auch für d-arrays funktionieren denn es funktioniert teoretisch auch für strings.
.Free kann aber net gehn ist ja kein Objekt.
und := nil ???
Soweit ich weiss sind die dynamischen arrays nicht im compiler implementiert sondern in einer seperaten unit wie soll die unit das setzen auf nil erkennen ?
Ich kann mir vorstellen das das compiliert und ausgeführt wird aber nicht das dabei Speicher freigegeben wird.
Warscheinlich crasht das programm dann beim verlassen der procedure.

@zummy
Note that the length of the array is set in elements, not in bytes of allocated memory (although these may be the same). The amount of memory allocated is the size of the array multiplied by the size of 1 element in the array. The memory will be disposed of at the exit of the current procedure or function.
hast du mal probiert on beim verlassen der Funktion der Speicher freigegeben wird ?!

procedure Fake;
var
s : array of byte;
begin
Setlength(s,1000000);
end;

begin
Fake;
//hier sollte wieder alles ok sein !?
end;
W.m.k.A.h.e.m.F.h. -> http://www.gidf.de/

Benutzeravatar
theo
Beiträge: 10856
Registriert: Mo 11. Sep 2006, 19:01

Beitrag von theo »

Christian hat geschrieben:Stimmt dynamische arrays gabs zu seinen zeiten noch nicht.
Sie sind aber an die normalen arrays angelehnt, und deren Syntax stammt vom Wirth.
Die Bemerkung mit Wirth war auch mehr auf deinen Satz:
"..Primz ist ne Variable und kein Objekt wenn Wirth tot wär.." gemünzt.
Meines wissens gab es bei Wirth kein TObject.free also dreht er sich wohl deswegen kaum im Grabe um. ;-)
Christian hat geschrieben: ..wie soll die unit das setzen auf nil erkennen ?
Ich kann mir vorstellen das das compiliert und ausgeführt wird aber nicht das dabei Speicher freigegeben wird.
Warscheinlich crasht das programm dann beim verlassen der procedure.
Manchmal plapperst du ein bisschen viel, wo doch nachsehen so einfach wär: "To remove a dynamic array's memory space we assign nil to the array variable"
Siehe auch z.B.:
http://www.drbob42.com/delphi4/dynarray.htm" onclick="window.open(this.href);return false;
http://delphi.about.com/od/beginners/a/arrays.htm" onclick="window.open(this.href);return false;

Christian
Beiträge: 6079
Registriert: Do 21. Sep 2006, 07:51
OS, Lazarus, FPC: iWinux (L 1.x.xy FPC 2.y.z)
CPU-Target: AVR,ARM,x86(-64)
Wohnort: Dessau
Kontaktdaten:

Beitrag von Christian »

Kann ich wohl nich wiedersprechen.
habs eben ausprobiert:
Funktionieren alle 3 Methoden mit fpc 2.1.1.
Verstehe dein Problem nun überhaupt nicht mehr, überwacht hab ichs übrigends sogar mit dem taskmanager.
W.m.k.A.h.e.m.F.h. -> http://www.gidf.de/

Antworten