amiga-news ENGLISH VERSION
.
Links| Forum| Kommentare| News melden
.
Chat| Umfragen| Newsticker| Archiv
.

amiga-news.de Forum > Programmierung > Listenobjekte und Speicherverwaltung [ - Suche - Neue Beiträge - Registrieren - Login - ]

-1- [ - Beitrag schreiben - ]

18.03.2005, 13:32 Uhr

DrNOP
Posts: 4118
Nutzer
Schalut schuschammen.

Ich hab' ja seither Embedded Software gemacht, die gut ohne Betriebssystem auskam. Neuerdings "darf" ich mich aber mit VxWorks rumschlagen und bin jetzt gerade auf die lstLib gestoßen. Ich geh' mal davon aus, daß das keine VxWorks-spezifische Bibliothek ist, drum stell' ich meine Frage hier:

Die Funktion lstDelete gibt ein Element einer doppelt verketteten List frei (sagt zumindest die Doku). Damit ist's aber auch schon fertig ... zumindest der Dokutext. :(
Bei der Funktion lstFree schreiben sie extra dazu, daß sie die Listenelemente löscht _und_ auch den Speicher freigibt. Der letzte halbe Satz fehlt bei der Funktion lstDelete. Ich würd's für reichlich blödsinnig halten, wenn die Funktion zwar das Element aus der Liste löscht, aber der Speicher weiterhin belegt bleibt.

Drauf gekommen bin ich, weil einer meiner zahlreichen Vorgänger dieses hier zusammengeschraubt hat:
code:
DATA_STRUCT *dataptr;
 DATA_STRUCT *tmpptr;

 dataptr = (DATA_STRUCT *)lstFirst(&ListStart);

 while(dataptr)
 {
 
   if ((dataptr->el1  == parm1) && (dataptr->el2 == parm2) &&
       (dataptr->el3  == parm3) && (dataptr->el4 == parm4) &&
       (dataptr->el5  == parm5) && (dataptr->el6 == parm6)) 
   {
     tmpptr = dataptr;
     lstDelete(&ListStart, (NODE *)dataptr);
     free(tmpptr);
     break;
   }
 
   dataptr = (DATA_STRUCT *)lstNext((NODE *)dataptr);
 }


Was mich daran nun wundert ist die Aktion mit dem free(tmpptr). Wozu ist das gut, den Pointer erst umzukopieren, aus der Liste zu löschen und dann "von Hand" den Speicher frei zu geben? :dance3:
--
Es gibt keine Notbremse für all den technischen Humbug, mit dem wir unsere Zeit vertrödeln.

[ - Antworten - Zitieren - Direktlink - ]

18.03.2005, 14:43 Uhr

Solar
Posts: 3680
Nutzer
Zitat:
Original von DrNOP:

Ich würd's für reichlich blödsinnig halten, wenn die Funktion zwar das Element aus der Liste löscht, aber der Speicher weiterhin belegt bleibt.


Manchmal ist Deine Liste nicht die einzige Referenz auf das Objekt. Denk' Dir eine Ready-Queue im Scheduler, aus der Du einen Task entfernen, aber die Taskstruktur nicht gleich löschen möchtest.

Zitat:
Was mich daran nun wundert ist die Aktion mit dem free(tmpptr). Wozu ist das gut, den Pointer erst umzukopieren, aus der Liste zu löschen und dann "von Hand" den Speicher frei zu geben?

Ich würde darauf tippen, daß Dein Vorgänger lstFree() nicht kannte.

[ - Antworten - Zitieren - Direktlink - ]

18.03.2005, 17:36 Uhr

DrNOP
Posts: 4118
Nutzer
Zitat:
Original von Solar:
Manchmal ist Deine Liste nicht die einzige Referenz auf das Objekt. Denk' Dir eine Ready-Queue im Scheduler, aus der Du einen Task entfernen, aber die Taskstruktur nicht gleich löschen möchtest.

Stimmt, könnte man haben. Aber hier sitzen die beiden Befehle ja direkt untereinander. Das fand ich so widersinnig. Das einzige, was dem sofortigen Löschen hier in die Quere kommen könnte wäre ein Interrupt. Und ob das ausgerechnet der ist, der noch was mit dem Element anfangen könnte?
Außerdem ist das Element doch eh' schon aus der Liste gelöscht, es kann niemand mehr darauf zugreifen, weil dieser Listenindex inzwischen auf ein anderes Element zeigt. Damit ist der Speicher doch tot, oder?

Zitat:
Ich würde darauf tippen, daß Dein Vorgänger lstFree() nicht kannte.
Ja, dachte ich auch erst. Aber zumindest in der Doku die ich hier habe, löscht lstFree() die ganze Liste, nicht nur ein einzelnes Element.
--
Es gibt keine Notbremse für all den technischen Humbug, mit dem wir unsere Zeit vertrödeln.

[ - Antworten - Zitieren - Direktlink - ]

18.03.2005, 19:34 Uhr

thomas
Posts: 7717
Nutzer
Zitat:
Außerdem ist das Element doch eh' schon aus der Liste gelöscht, es kann niemand mehr darauf zugreifen, weil dieser Listenindex inzwischen auf ein anderes Element zeigt.

Ähm, Listenindex ? Du verwechselst eine verkettete Liste mit einer Tabelle.

Normalerweise werden beim Entfernen eines Elements aus einer Liste nur die Pointer der benachbarten Elemente verändert, die Daten des entfernten Elements bleiben unberührt.

In deinem Beispiel oben finde ich z.B. den Umstand mit dem tmpptr vollkommen unnötig. Dataptr zeigt nach meinem Verständnis nach dem lstDelete nach wie vor auf das gültige Element, nur daß es nicht mehr Teil einer Liste ist.

Stell es dir so vor:

Vorher:
code:
ListStart  --->  element1        element2       element3
                   next   ---->   next    ---->   next  ---->  NULL
       NULL <--- previous <----  previous <---- previous
                  Daten1          Daten2         Daten3


lstDelete (ListStart,element2);

code:
ListStart  --->  element1      element3                element2     
                   next   --->   next  ---->  NULL       next   
       NULL <--- previous <--- previous                previous 
                  Daten1        Daten3                  Daten2


Was geändert wurde ist element1.next und element3.previous. Element2 ist vollkommen unberührt geblieben. Es steht noch immer an der gleichen Stelle im Speicher, auch wenn ich es aus zeichnerischen Gründen hier nach rechts gelegt habe. Erst durch ein free(element2) würde der Speicher freigegeben.

Der Sinn ist z.B. folgender: stell dir nochmal den Scheduler vor. Du hast eine Ready-Queue und eine Waiting-Queue. Wenn eine Task auf der Ready-Queue einen Wait-Befehl ausführt, wird die Task-Struktur aus der Ready-Queue entfernt und an die Waiting-Queue angehängt. Dazu können die gleichen Pointer in der Task-Struktur benutzt werden.

Gruß Thomas

--
Email: thomas-rapp@web.de
Home: home.t-online.de/home/thomas-rapp/

[ Dieser Beitrag wurde von thomas am 18.03.2005 editiert. ]

[ - Antworten - Zitieren - Direktlink - ]

18.03.2005, 23:55 Uhr

DrNOP
Posts: 4118
Nutzer
Zitat:
Original von thomas:
Ähm, Listenindex ? Du verwechselst eine verkettete Liste mit einer Tabelle.

Nein, drum ja Listen- und nicht Tabellenindex ;)
Ich nahm an, daß diese Unterscheidung für meine Frage unerheblich sei; jedenfalls stehen die Elemente irgendwie in einer festen Reihenfolge, so wie du sie in deinem Beispiel ja auch durchnumeriert hast. Und egal ob ich vorher schon mal auf das 5. Element zugegriffen habe oder mich vom Listenanfang durchhangle, ich finde dieses Element nicht wieder, weil es gerade gelöscht wurde. Aber ein Element von einer Liste in eine andere zu übertragen, macht natürlich Sinn. Dafür sollte man die Datenstruktur noch im Speicher stehen haben ... ;)

Zitat:
[...]
Was geändert wurde ist element1.next und element3.previous. Element2 ist vollkommen unberührt geblieben. Es steht noch immer an der gleichen Stelle im Speicher, auch wenn ich es aus zeichnerischen Gründen hier nach rechts gelegt habe. Erst durch ein free(element2) würde der Speicher freigegeben.

Damit hast du, wahrscheinlich ohne es zu merken, meine ursprüngliche Frage beantwortet, die da lautete:
Löscht lstDelete das Element aus der Liste _und_ gibt den belegten Speicher frei? Nach deiner Erklärung hier stelle ich fest:
Nein. Ist das so weit richtig?
Dann macht wenigstens das free() darunter Sinn. Allerdings könnte statt free(tmpptr) auch gleich free(dataptr) nehmen. Auch richtig?

--
Es gibt keine Notbremse für all den technischen Humbug, mit dem wir unsere Zeit vertrödeln.

[ - Antworten - Zitieren - Direktlink - ]


-1- [ - Beitrag schreiben - ]


amiga-news.de Forum > Programmierung > Listenobjekte und Speicherverwaltung [ - Suche - Neue Beiträge - Registrieren - Login - ]


.
Impressum | Datenschutzerklärung | Netiquette | Werbung | Kontakt
Copyright © 1998-2024 by amiga-news.de - alle Rechte vorbehalten.
.