ここでのジョン・フェントンの投稿に対する私のコメントを説明するのが私の答えです。次の例を見てみましょう。
class Program
{
static void Main(string[] args)
{
var a = new A();
var b = new B();
a.Clicked += b.HandleClicked;
//a.Clicked += B.StaticHandleClicked;
//A.StaticClicked += b.HandleClicked;
var weakA = new WeakReference(a);
var weakB = new WeakReference(b);
a = null;
//b = null;
GC.Collect();
GC.WaitForPendingFinalizers();
GC.Collect();
Console.WriteLine("a is alive: " + weakA.IsAlive);
Console.WriteLine("b is alive: " + weakB.IsAlive);
Console.ReadKey();
}
}
class A
{
public event EventHandler Clicked;
public static event EventHandler StaticClicked;
}
class B
{
public void HandleClicked(object sender, EventArgs e)
{
}
public static void StaticHandleClicked(object sender, EventArgs e)
{
}
}
あなたが持っている場合
a.Clicked += b.HandleClicked;
b のみを null に設定すると、weakA と weakB の両方の参照が有効になります。a のみを null に設定すると、b は存続しますが、a は存続しません (これは、ハード参照がイベント プロバイダー (この場合は a) に格納されていると述べた John Fenton が間違っていることを証明しています)。
これは私を間違った結論に導きました
a.Clicked += B.StaticHandleClicked;
のインスタンスが静的ハンドラーによって保持されるため、リークが発生する可能性があります。これは当てはまりません (私のプログラムをテストしてください)。静的イベント ハンドラーまたはイベントの場合は、逆になります。あなたが書くなら
A.StaticClicked += b.HandleClicked;
b への参照が保持されます。