C # Timer und Garbage Collection

8

Laut MSDN , eine Referenz zu System.Threading.Timer sollte beibehalten werden, sonst wird es Müll-gesammelt. Wenn ich diesen Code ausführe, schreibt er keine Nachricht (was das erwartete Verhalten ist):

%Vor%

Wenn ich jedoch den Code leicht modifiziere, indem ich den Timer in einer temporären lokalen Variablen speichere, überlebt er und schreibt die Nachricht:

%Vor%

Während der Garbage-Collection gibt es offensichtlich keine Möglichkeit, auf den Timer von Root- oder statischen Objekten zuzugreifen. Kannst du mir bitte erklären, warum der Timer überlebt? Wo ist die Referenz erhalten?

    
Peter Smolinsky 07.06.2016, 14:02
quelle

1 Antwort

3

Jedes Timer verweist auf ein TimerHolder , das auf ein TimerQueueTimer verweist. Die Implementierung behält über den Aufruf von TimerQueueTimer UpdateTimer() >.

Unter normalen Umständen können Sie Ihren Timer kostenlos sammeln, finalisieren Sie den TimerHolder und Entfernen der TimerQueueTimer aus der internen Warteschlange. Aber der einfache Konstruktor Timer(TimerCallback) ruft TimerSetup() mit Timer selbst auf als der Staat. In diesem speziellen Fall verweist der Zustand TimerQueueTimer also auf Timer und verhindert, dass er gesammelt wird.

Der Effekt hängt nicht mit dem Beibehalten einer temporären lokalen Variablen zusammen. Es passiert einfach wegen der Interna des Timer -Mechanismus. Es ist viel klarer und sicherer, einen Verweis auf Ihren Timer zu halten, wie von MSDN empfohlen.

    
piedar 07.06.2016, 19:05
quelle

Tags und Links