By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
434,984 Members | 2,832 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 434,984 IT Pros & Developers. It's quick & easy.

question about default destructors...

P: n/a
Hello,

Are default destructors virtual?

In other words, say I have "class A" and "class B : public A", and I
have the code below:

A * a = new A;
B * b = new B;
a = b;
delete a;

Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?

Jun 14 '07 #1
Share this Question
Share on Google+
12 Replies


P: n/a
On Jun 13, 10:35 pm, Avalon1178 <Avalon1...@gmail.comwrote:
Hello,

Are default destructors virtual?
No, they are not. The rationale is that you should not have to pay for
features you don't use, and sone classes do not need virtual
destructors.

Jun 14 '07 #2

P: n/a

"Avalon1178" wrote:
Are default destructors virtual?
Nope. Just last night, my compiler (gcc) warned me:
"Warning: class has virtual functions but non-virtual
destructor".

You really only need a virtual destructor if your base class
has virtual functions, and if your derived classes have data
members that need to be destructed differently than than the
base class.
In other words, say I have "class A" and "class B : public A",
and I have the code below:

A * a = new A;
B * b = new B;
a = b;
delete a;

Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?
That will call A's destructor. If B has dynamically-allocated
data members which A doesn't, that will create a memory leak.
In a case like that, you should put this line in A:

class A
{
public:
A();
virtual ~A();
...
private:
...
};

Then make B's destructor do whatever it needs to do. (Such
as calling "delete" for new'd data members.)

class B : public A
{
public:
B() {Blat = new double;}
~B() {delete Blat;}
...
private:
double *Blat;
...
};

Then if you do this in main():

int main (void)
{
A* Fred = new B;
delete Fred; // calls ~B(), not ~A()
return 42;
}

Fred will then get correctly destructed.

--
Cheers,
Robbie Hatley
lone wolf aatt well dott com
triple-dubya dott Tustin Free Zone dott org
Jun 14 '07 #3

P: n/a
int main (void)
{
A* Fred = new B;
delete Fred; // calls ~B(), not ~A()
IIRC, ~A() will still be called after the B object is destructed.

Jun 14 '07 #4

P: n/a
On Jun 14, 1:35 pm, Avalon1178 <Avalon1...@gmail.comwrote:
Hello,

Are default destructors virtual?

In other words, say I have "class A" and "class B : public A", and I
have the code below:

A * a = new A;
B * b = new B;
a = b;
delete a;

Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?

No, compiler won't generate default virtual desctrutor.
Once you delete a, it will just invoke A's destructor of course.
You can debug this sample code in the IDE and check whether there is
vptr.

Jun 14 '07 #5

P: n/a
On Jun 14, 9:35 am, Avalon1178 <Avalon1...@gmail.comwrote:
Hello,

Are default destructors virtual?

In other words, say I have "class A" and "class B : public A", and I
have the code below:

A * a = new A;
B * b = new B;
a = b;
delete a;

Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?
it calls A .but from the point at which you define a virtual
destructor ,subsequent derived classes will have virtual versions of
dtor eventhough you do not declare any:

struct A{};
struct B:A{virtual ~B(){};};
struct C:B{};
struct D:C{~D{};};

A* a = new B;
delete a;//call A`s dtor .dtor is not virtual yet

B* b = new c;
delete b;//call C`s dtor. after B dtor will be virtual

delete (b = new D);//call D`s dtor

C* c = new D;
delete c;//call D`s dtor

regards,
FM

Jun 14 '07 #6

P: n/a
On Jun 14, 8:38 am, "Robbie Hatley"
<see.my.signat...@for.my.email.addresswrote:
"Avalon1178" wrote:
Are default destructors virtual?
Nope. Just last night, my compiler (gcc) warned me:
"Warning: class has virtual functions but non-virtual
destructor".
You really only need a virtual destructor if your base class
has virtual functions, and if your derived classes have data
members that need to be destructed differently than than the
base class.
I don't know where you got that from, but it is completely
false. If you delete an object of a derived type through a
pointer to the base type, the destructor must be virtual in the
base type. It certainly has nothing to do with what is or is
not present in the derived class---if the dynamic type is
different from the static type, either the destructor in the
static type is virtual, or you have undefined behavior.

Typically, of course, if a class doesn't have virtual functions,
there's no point in deriving from it, or at least, there's no
point in having a pointer to it when the actual object has a
derived type. So typically, if you don't have virtual
functions, you don't need a virtual destructor. Typically;
there are a few rare cases where you might use some sort of
labeling interface, which has no functions of its own.
In other words, say I have "class A" and "class B : public A",
and I have the code below:
A * a = new A;
B * b = new B;
a = b;
delete a;
Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?
That will call A's destructor.
Maybe. I might also crash the system. Or reformat your hard
drive. It's undefined behavior.

--
James Kanze (GABI Software, from CAI) email:ja*********@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

Jun 14 '07 #7

P: n/a
Avalon1178 wrote:
Hello,

Are default destructors virtual?
No.
>
Neither A or B have destructors defined (thus creating a default
destructor for each), when "delete a" is called, will it call b's
destructor first then a's destructor, or will it just call a's
destructor?
It's worse than the destructors not being called right. It's
outright undefined behavior. The language specifically requires
a virtual destructor to delete derived objects through that type.
The implementation is free to key all sorts of stuff (like the
deallocation function) off the presence of the virtual destructor.
Jun 14 '07 #8

P: n/a
"Robbie Hatley" <se**************@for.my.email.addresswrote in message
news:ln*******************@fe02.news.easynews.com. ..
You really only need a virtual destructor if your base class
has virtual functions, and if your derived classes have data
members that need to be destructed differently than than the
base class.
Not true. You need a virtual destructor in your base class whenever you use
a pointer to base to delete a derived-class object. Just because your
implementation happens not to enforce the rule doesn't make the rule go
away.
Jun 14 '07 #9

P: n/a
<in*************@gmail.comwrote in message
news:11*********************@j4g2000prf.googlegrou ps.com...
>int main (void)
{
A* Fred = new B;
delete Fred; // calls ~B(), not ~A()

IIRC, ~A() will still be called after the B object is destructed.
If class A does not have a virtual destructor, the effect of this example is
undefined, which means that anything could happen.
Jun 14 '07 #10

P: n/a
"Ge Chunyuan" <hh****@gmail.comwrote in message
news:11**********************@q19g2000prn.googlegr oups.com...
>
>A * a = new A;
B * b = new B;
a = b;
delete a;
No, compiler won't generate default virtual desctrutor.
Once you delete a, it will just invoke A's destructor of course.
Maybe yes, maybe no.
Jun 14 '07 #11

P: n/a
On Jun 14, 8:30 pm, terminator <farid.mehr...@gmail.comwrote:
struct A{};
struct B:A{virtual ~B(){};};
struct C:B{};
struct D:C{~D{};};

A* a = new B;
delete a;//call A`s dtor .dtor is not virtual yet
No, this causes undefined behaviour. (As has been
pointed out several times on this thread already
but I thought I'd mention it again in case anyone
was under the impression that this example is
different to the other examples presented).
B* b = new c;
I guess you mean C rather than c.
delete b;//call C`s dtor.
Calls C's dtor and then B's dtor, to be precise.
delete (b = new D);//call D`s dtor
Is that legal? i.e. delete (X=Y)
First impression is that it might fall foul of
sequence point rules and/or the rule about
accessing the result of an assignment.

Jun 14 '07 #12

P: n/a
On Jun 15, 1:26 am, Old Wolf <oldw...@inspire.net.nzwrote:
On Jun 14, 8:30 pm, terminator <farid.mehr...@gmail.comwrote:
delete (b = new D);//call D`s dtor
Is that legal? i.e. delete (X=Y)
First impression is that it might fall foul of
sequence point rules and/or the rule about
accessing the result of an assignment.
Good question. I think it is, because delete resolves to a
function call (or two, if there is a destructor), and a function
call implies a sequence point; if b is a global variable, and
the destructor of D reads it, it must see the effect of the
assignment, and if the global operator delete has been replaced,
it must also see the effect of the assignment.

On the other hand, it doesn't look too useful, and I don't think
I'd recommend it in production code.

--
James Kanze (GABI Software, from CAI) email:ja*********@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34

Jun 15 '07 #13

This discussion thread is closed

Replies have been disabled for this discussion.