Es gab eine Menge Diskussion darüber und jeder stimmt zu, dass Sie immer Delegate.EndInvoke aufrufen sollten, um ein Speicherleck zu verhindern (sogar Jon Skeet hat es gesagt!).Kein Aufruf von Delegate.EndInvoke kann Speicherverlust verursachen ... ein Mythos?
Ich folgte dieser Richtlinie immer ohne zu hinterfragen, aber vor kurzem implementierte ich meine eigene AsyncResult-Klasse und sah, dass die einzige Ressource, die auslaufen könnte, die AsyncWaitHandle ist.
(In der Tat ist es nicht wirklich leck, weil die native Ressource von der WaitHandle ist in einem SafeHandle verkapselt, die einen Finalizer hat, wird es Druck auf die Finalize-Warteschlange des Garbage Collector obwohl. Trotzdem, eine gute Implementierung von AsyncResult die AsyncWaitHandle auf Nachfrage ...)
der beste Weg, zu wissen, nur initialisieren, wenn ein Leck vorhanden ist, wird es nur versuchen:
Action a = delegate { };
while (true)
a.BeginInvoke(null, null);
ich lief dies für eine Weile und dem Speicher Bleiben Sie zwischen 9-20 MB.
Vergleichen wir mit, wenn Delegate.EndInvoke genannt wird:
Action a = delegate { };
while (true)
a.BeginInvoke(ar => a.EndInvoke(ar), null);
Mit diesem Test der Speicher Spiel zwischen 9-30 MG, komisch oder? (Wahrscheinlich, weil es etwas länger dauert, wenn ein AsyncCallback ausgeführt wird, so dass es mehr Delegierte in der ThreadPool-Warteschlange gibt)
Was denken Sie ... "Mythos kaputt"?
P.S. ThreadPool.QueueUserWorkItem ist hundert effizienter als Delegate.BeginInvoke, es ist besser, es für Feuer & Anrufe zu vergessen.
Gute Frage! +1. BTW, du guckst zuviel MythBusters;) – RCIX
Dem stimme ich zu, ThreadPool.QueueUserWorkItem ist eine geniale und wenig genutzte Methode. – Anton