I think this is a C# beginner question, but I can't seem to find a correct solution.
I have a ClassOne object, which defines an event. I create a ClassTwo object, which is considered as a black box, which means I don't know whether it will register to any event or not. ClassTwo constructor registers to the event of ClassOne. The problem comes, when ClassTwo object goes out of scope. The garbage collector never deletes this object, because it never deregistered the event.
So I have two questions:
Is there a way for ClassTwo object to know, when it goes out of scope? For an old C++ programmer this would be in the destructor, but with C# this doesn't work.
Is there a debug tool which helps me to find such objects?
Here is a sample code to reproduce the issue:
public partial class MainWindow : Window
{
static public ClassOne classOne = new ClassOne();
public MainWindow()
{
InitializeComponent();
ClassTwo classtwo = new ClassTwo();
}
private void buttonTest_Click(object sender, RoutedEventArgs e)
{
GC.Collect();
}
}
public class ClassOne
{
public ClassOne()
{
Trace.WriteLine(this + " constructor");
}
~ClassOne()
{
Trace.WriteLine(this + " destructor");
}
public delegate void UpdateFunc(object sender, EventArgs args);
public event UpdateFunc OnUpdate;
}
public class ClassTwo
{
public ClassTwo()
{
Trace.WriteLine(this + " constructor");
MainWindow.classOne.OnUpdate += new ClassOne.UpdateFunc(classOne_OnUpdate);
}
void classOne_OnUpdate(object sender, EventArgs args)
{
throw new NotImplementedException();
}
~ClassTwo()
{
Trace.WriteLine(this + " destructor");
}
}
I would implement IDisposable
on an object like this and unregister from the event in the Dispose
method.
You would use your object like this:
using(var two = new ClassTwo(classOne))
{
// Do something with two
}
// object can now be garbage collected.
If the caller fails to call Dispose
, you are out of luck.
Not unless it implements IDisposable
and the caller cooperates by calling Dispose
correctly.
(Of course, why wouldn't the caller cooperate?)
Not that I've of. :( I think your best bet is to implement IDisposable
and unregister on Dispose
.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With