Kann jemand erklären, was der Punkt ist, an dem ein Objekt annulliert wird, bevor es seinen Gültigkeitsbereich verlässt?

7

Ich habe an einigen Stellen Code mit folgender Logik gesehen:

%Vor%

Was ist der Grund dafür, foo im Wörterbuch auf null zu stellen, bevor Sie es entfernen?

Ich dachte, die Garbage-Collection interessiert sich für die Anzahl der Dinge, die auf den ursprünglichen * foo verweisen. Wenn das der Fall ist, würde die Einstellung von myDictonary ["foo"] auf null nicht einfach die Anzahl um eins verringern? Würde nicht dasselbe passieren, wenn myDictonary.Remove ("foo") aufgerufen wird?

Was ist der Punkt von _myDictonary ["foo"] = null;

edit: Zur Klärung - als ich sagte "entferne die Zählung um eins" meinte ich folgendes:
- myDictonary ["foo"] zeigt ursprünglich auf ein Objekt. Das bedeutet, das Objekt hat ein oder mehrere Dinge, die darauf verweisen.
- Sobald myDictonary ["foo"] auf null gesetzt ist, verweist es nicht mehr auf dieses Objekt. Dies bedeutet, dass Objekt eine weniger Sache hat, die darauf verweist.

    
JSWork 07.03.2011, 17:44
quelle

8 Antworten

13

Es gibt überhaupt keinen Sinn.

Wenn Sie sich ansehen, was die Methode Remove tut (mit .NET Reflector), finden Sie Folgendes:

%Vor%

Diese Zeile setzt den Wert des Wörterbuchelements auf null, da der Standardwert für einen Referenztyp null ist. Wenn also die Remove -Methode den Verweis auf Null setzt, hat es keinen Sinn, dies vor dem Aufruf der Methode zu tun.

    
Guffa 07.03.2011, 17:57
quelle
4

Wenn Sie einen Wörterbucheintrag auf null setzen, verringert nicht die ref-Zählung, da null ein perfekt geeigneter Wert ist, auf den in einem Wörterbuch verwiesen wird.

Die beiden Aussagen machen sehr unterschiedliche Dinge. Wenn Sie den Wert auf null setzen, bedeutet dies, dass der Wert für diesen Schlüssel sein sollte, während das Entfernen dieses Schlüssels aus dem Wörterbuch anzeigt, dass er nicht mehr vorhanden sein sollte.

    
Daniel DiPaolo 07.03.2011 17:45
quelle
4

Es gibt nicht viel Sinn.

Wenn jedoch die Remove -Methode Heapzuweisungen verursacht und der gespeicherte Wert groß ist, kann beim Aufruf von Remove eine Garbage Collection erfolgen, und der Wert kann auch im Prozess gesammelt werden (wodurch möglicherweise Speicher freigegeben wird) ). In der Praxis kümmern sich die Leute normalerweise nicht um kleine Dinge wie diese, es sei denn, sie wurden gezeigt , um nützlich zu sein.

Bearbeiten:

Vergessen zu erwähnen: Im Idealfall sollte sich das Wörterbuch selbst um seine eigene Implementierung kümmern, nicht den Anrufer.

    
Mehrdad 07.03.2011 17:46
quelle
1

Es macht dort nicht viel Sinn, aber es gibt Zeiten, in denen es Sinn macht.

Ein Beispiel ist in einer Dispose() -Methode. Betrachte diesen Typ:

%Vor%

Sie könnten jetzt argumentieren, dass dies unnötig ist, und Sie haben meistens Recht. Normalerweise Dispose() wird nur aufgerufen, bevor Owner dereferenziert wird, und wenn Owner gesammelt wird, wird _bigAllocation ebenfalls ... schließlich.

Allerdings:

Wenn _bigAllocation auf null gesetzt wird, ist es sofort für die Sammlung geeignet , wenn niemand sonst einen Verweis darauf hat. Dies kann vorteilhaft sein, wenn Owner in einer GC-Generation mit höherer Nummer steht oder einen Finalizer hat. Andernfalls muss Owner freigegeben werden, bevor _bigAllocation für die Erfassung ausgewählt werden kann.

Dies ist jedoch eine Art Eckfall. Die meisten Typen sollten keine Finalizer haben und in den meisten Fällen wären _bigAllocation und Owner in derselben Generation.

    
Craig Stuntz 07.03.2011 19:11
quelle
0

Ich könnte mir vorstellen, dass dies in einer Multithread-Anwendung nützlich ist, in der Sie das Objekt auf null setzen, damit kein anderer Thread darauf operieren kann. Allerdings scheint dies schwer zu handhaben und schlechtes Design.

    
Ryan Bennett 07.03.2011 17:51
quelle
0
  
    

Wenn dies der Fall ist, würde myDictonary ["foo"] nicht auf null gesetzt     einfach die Anzahl um eins verringern?

  

Nein, die Anzahl ändert sich nicht, der Verweis befindet sich immer noch im Wörterbuch, er zeigt auf Null.

Ich sehe keinen Grund dafür, dass der Code so ist.

    
Steve Wellens 07.03.2011 17:55
quelle
0

Ich weiß nichts über die Interna von Dictionary im Speziellen, aber einige Arten von Sammlungen können Referenzen auf Objekte enthalten, die tatsächlich "tot" sind. Zum Beispiel kann eine Sammlung ein Array und eine Anzahl von wie vielen gültigen Elementen in dem Array enthalten; Wenn die Zählung auf null gesetzt würde, würden alle Elemente in der Sammlung nicht zugänglich sein, aber sie würden keine Referenzen auf sie zerstören. Es kann sein, dass das Löschen eines Elements aus einem Dictionary dazu führt, dass der Bereich, in dem das Objekt enthalten ist, wiederverwendet werden kann, ohne es tatsächlich zu löschen. Wenn ein anderes Element mit dem gleichen Hash-Code zum Wörterbuch hinzugefügt wird, wird das erste Element tatsächlich gelöscht, aber das passiert möglicherweise nie für eine Weile.

    
supercat 07.03.2011 17:55
quelle
0

Das sieht nach einer alten C ++ Gewohnheit aus.

Ich vermute, dass der Autor sich Sorgen um ältere Sammlungen und / oder andere Sprachen macht. Wenn Speicher dient, würden einige Auflistungen in C ++ Zeiger auf die gesammelten Objekte enthalten, und wenn "entfernt" nur den Zeiger entfernen würde, aber nicht automatisch den Destruktor des neu entfernten Objekts aufrufen würde. Dies verursacht einen sehr subtilen Speicherverlust. Die Gewohnheit wurde, das Objekt auf null zu setzen, bevor es entfernt wurde, um sicherzustellen, dass der Destruktor aufgerufen wurde.

    
Kelly S. French 21.04.2011 15:26
quelle

Tags und Links