Destructor not being called - why?

  • Thread starter Thread starter renegade_master_12121
  • Start date Start date
R

renegade_master_12121

Here is a Test.

formtest.cs:


class MyForm : System.Windows.Forms.Form {

void Dump(string s){
System.IO.StreamWriter sw = new
System.IO.StreamWriter("dumpfile.txt", true);
sw.WriteLine(s, System.DateTime.Now);
sw.Close();
}

public MyForm(){
Dump("ctor");
}
~MyForm(){
Dump("dtor");
}

}

class TestForm {

static void Main(){
MyForm x = new MyForm();
System.Windows.Forms.Application.Run(x);
}
}


This file defines a form and has a Main() which creates a form and
passes it to Application.Run(). However the destructor for the form
never seems to get called; the dumpfile.txt only ever mentions the
ctor call. What am I doing wrong or misunderstanding here? Thanks.
 
At a guess (without testing):

When the form is closed, it is also Dispose()d (pehaps by Close()
itself, perhaps by Application.Run()). The normal pattern for
Dispose() on a class with a finalizer is to tell the garbage collector
(GC) that we are clean, and don't need finalizing. Hence, Dispose()
gets called, but the finalizer does not.

Perhaps override Dispose(bool disposing); if disposing is true, then
you are being called via Dispose() and you can still talk to any
undisposed objects you can see. If disposing is false you are being
called via the finalizer, and you shouldn't attempt to talk to any
managed objects (since they may be in an indeterminate state); you
should just release any unmanaged resources you have (e.g. windows
handles, native files, etc).

Marc
 
That is because the Component (the base class of the Form) has the
..Dispose method is looked like this:

Component.Dispose()
{
this.Dispose(true);
GC.SuppressFinalize(this);
}

The calling of System.GC::SuppressFinalize on the object disposed remove
it from the Finalization queue and Finalize method (destructor in C#)
will never be called.

Put your logging in the Dispose method and everything will work fine:

protected override void Dispose(bool disposing)
{
...
Dump("dtor");
...
}

Regards, Alex Meleta
Blog:: http://devkids.blogspot.com

-----Original Message-----
From: (e-mail address removed)
[mailto:[email protected]]
Posted At: Tuesday, April 24, 2007 12:34 PM
Posted To: microsoft.public.dotnet.languages.csharp
Conversation: Destructor not being called - why?
Subject: Destructor not being called - why?

Here is a Test.

formtest.cs:


class MyForm : System.Windows.Forms.Form {

void Dump(string s){
System.IO.StreamWriter sw = new
System.IO.StreamWriter("dumpfile.txt", true);
sw.WriteLine(s, System.DateTime.Now);
sw.Close();
}

public MyForm(){
Dump("ctor");
}
~MyForm(){
Dump("dtor");
}

}

class TestForm {

static void Main(){
MyForm x = new MyForm();
System.Windows.Forms.Application.Run(x);
}
}


This file defines a form and has a Main() which creates a form and
passes it to Application.Run(). However the destructor for the form
never seems to get called; the dumpfile.txt only ever mentions the
ctor call. What am I doing wrong or misunderstanding here? Thanks.
 
At a guess (without testing):

When the form is closed, it is also Dispose()d (pehaps by Close()
itself, perhaps by Application.Run()). The normal pattern for
Dispose() on a class with a finalizer is to tell the garbage collector
(GC) that we are clean, and don't need finalizing. Hence, Dispose()
gets called, but the finalizer does not.

Also, I don't think there is any guarantee that finalizes will be
called at all.
 
Andy said:
Also, I don't think there is any guarantee that finalizes will be
called at all.


It's not because it's not guaranteed 100% that they aren't called most of
the time, chances that the finalizer doesn't run is extremely low.

Willy.
 
Back
Top