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

why virtual base dtor gets called?

P: n/a
Is it correct that the virtual dtor of base gets called implicitly?
Here's some code to demonstrate what I mean:
Class B has a virtual destructor, so has class D which
is derived from B. Deleting D calls the dtor of D and
then the dtor of B.
I was thinking that this would be true only for non-virtual dtor case,
but I wouldn't have expected it happen for a virtual dtor.
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.
What's correct? Is maybe my compiler buggy?

class B
{
public:
B() {}
virtual ~B() { std::cout << "~B\n"; }
};

class D : public B
{
public:
D() {}
virtual ~D() { std::cout << "~D\n"; }
};

void virtual_dtor_tester()
{
B b;
D d;
}

/* output:
~D
~B
~B
*/
Jul 23 '05 #1
Share this Question
Share on Google+
27 Replies


P: n/a
> For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.


Nope. Since D is a B, the base part of D must be destroyed, hence ~B() is
called.
That is always true regardless of whether B or D contains virtual functions.

Compiler is correct.

Stephen Howe
Jul 23 '05 #2

P: n/a

"tuvok" <52***************@t-online.de> wrote in message
news:d8*************@news.t-online.com...
Is it correct that the virtual dtor of base gets called implicitly?
Not really, the virtual d~tor of base class is invoked, not called.
Here's some code to demonstrate what I mean:
Class B has a virtual destructor, so has class D which
is derived from B. Deleting D calls the dtor of D and
then the dtor of B.
B's d~tor is invoked and processed before D's d~tor can complete.
I was thinking that this would be true only for non-virtual dtor case,
but I wouldn't have expected it happen for a virtual dtor.
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.
You are describing a non-virtual d~tor. Only D's d~tor would be invoke.
Which is the crux of the arguement of why a derived class needs the base to
have the virtual d~tor.
What's correct? Is maybe my compiler buggy?

class B
{
public:
B() {}
virtual ~B() { std::cout << "~B\n"; }
};

class D : public B
{
public:
D() {}
virtual ~D() { std::cout << "~D\n"; }
};

void virtual_dtor_tester()
{
B b;
D d;
}

/* output:
~D
~B
~B
*/


Try:

#include <iostream>

class B
{
public:
B() { std::cout << "B\n"; }
virtual ~B() { std::cout << "~B\n"; }
};

class D : public B
{
public:
D() { std::cout << "D\n"; }
~D() { std::cout << "~D\n"; }
};

class E : public D
{
public:
E() { std::cout << "E\n"; }
~E() { std::cout << "~E\n"; }
};
int main(int argc, char* argv[])
{
E e;

return 0;
}

/*
B
D
E
~E
~D
~B
*/

Note: d~tors ~D() and ~E() are automatically virtual.

Jul 23 '05 #3

P: n/a
Peter Julian wrote:
tuvok wrote:
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.
You are describing a non-virtual d~tor. Only D's d~tor would be
invoke. Which is the crux of the arguement of why a derived class
needs the base to have the virtual d~tor.


Please don't answer questions here if you don't know what
you are talking about. Invoking a derived class's destructor
ALWAYS calls the base class destructors.

The virtualness of the base class destructor only comes into
play when the object is deleted via a pointer to the base
class.
Try:

#include <iostream>

class B
{
public:
B() { std::cout << "B\n"; }
virtual ~B() { std::cout << "~B\n"; }
};

class D : public B
{
public:
D() { std::cout << "D\n"; }
~D() { std::cout << "~D\n"; }
};

class E : public D
{
public:
E() { std::cout << "E\n"; }
~E() { std::cout << "~E\n"; }
};
int main(int argc, char* argv[])
{
E e;

return 0;
}

/*
B
D
E
~E
~D
~B
*/


The output will be the same even if B's dtor is not virtual.
Try it and see.

Jul 23 '05 #4

P: n/a
"Peter Julian" wrote

"tuvok" wrote in message
Is it correct that the virtual dtor of base gets called implicitly?
Not really, the virtual d~tor of base class is invoked, not called.
Here's some code to demonstrate what I mean:
Class B has a virtual destructor, so has class D which
is derived from B. Deleting D calls the dtor of D and
then the dtor of B.


B's d~tor is invoked and processed before D's d~tor can complete.
I was thinking that this would be true only for non-virtual dtor case,
but I wouldn't have expected it happen for a virtual dtor.
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.


You are describing a non-virtual d~tor. Only D's d~tor would be invoke.


No, it's not the case. Both ~D and ~B are invoked no matter whether
the dtors are virtual or not. So there seems no difference whether
the dtors are virtual or not. Ie. always the dtors of all parts get invoked.
Which is the crux of the arguement of why a derived class needs the base to
have the virtual d~tor.

Jul 23 '05 #5

P: n/a
The code below illustrates the difference between the virtual (V) and
non-virtual (NV) cases. The difference occurs when you have a base pointer
to a derived class.
#include <iostream>

class BaseV
{
public:
BaseV() { std::cout << "BaseV\n"; }
virtual ~BaseV() { std::cout << "~BaseV\n"; }
};

class DerivedV : public BaseV
{
public:
DerivedV() { std::cout << "DerivedV\n"; }
~DerivedV() { std::cout << "~DerivedV\n"; }
};

class BaseNV
{
public:
BaseNV() { std::cout << "BaseNV\n"; }
~BaseNV() { std::cout << "~BaseNV\n"; }
};

class DerivedNV : public BaseNV
{
public:
DerivedNV() { std::cout << "DerivedNV\n"; }
~DerivedNV() { std::cout << "~DerivedNV\n"; }
};
int main(int argc, char* argv[])
{
BaseV *ptrV = new DerivedV;
delete ptrV;

BaseNV *ptrNV = new DerivedNV;
delete ptrNV;
}
--
John Carson

Jul 23 '05 #6

P: n/a
"John Carson" wrote
The code below illustrates the difference between the virtual (V) and
non-virtual (NV) cases. The difference occurs when you have a base pointer
to a derived class.
#include <iostream>

class BaseV
{
public:
BaseV() { std::cout << "BaseV\n"; }
virtual ~BaseV() { std::cout << "~BaseV\n"; }
};

class DerivedV : public BaseV
{
public:
DerivedV() { std::cout << "DerivedV\n"; }
~DerivedV() { std::cout << "~DerivedV\n"; }
};

class BaseNV
{
public:
BaseNV() { std::cout << "BaseNV\n"; }
~BaseNV() { std::cout << "~BaseNV\n"; }
};

class DerivedNV : public BaseNV
{
public:
DerivedNV() { std::cout << "DerivedNV\n"; }
~DerivedNV() { std::cout << "~DerivedNV\n"; }
};
int main(int argc, char* argv[])
{
BaseV *ptrV = new DerivedV;
delete ptrV;

BaseNV *ptrNV = new DerivedNV;
delete ptrNV;
}


I see. Thanks.
I've slightly extended it to show the difference also vs. stack objects:

void test_virt_vs_nonvirt_dtor()
{
std::cout << "Derived objects created on stack:\n";
{
std::cout << " Creating:\n";
DerivedV dv;
DerivedNV dnv;
std::cout << " Destroying:\n";
}

std::cout << "\nDerived objects using ptr to base created on heap:\n";
std::cout << " Creating:\n";
BaseV *ptrV = new DerivedV;
BaseNV *ptrNV = new DerivedNV;
std::cout << " Destroying:\n";
delete ptrNV;
delete ptrV;
}

Here's the output:

Derived objects created on stack:
Creating:
BaseV
DerivedV
BaseNV
DerivedNV
Destroying:
~DerivedNV
~BaseNV
~DerivedV
~BaseV

Derived objects using ptr to base created on heap:
Creating:
BaseV
DerivedV
BaseNV
DerivedNV
Destroying:
~BaseNV
~DerivedV
~BaseV

So, bottom line is: using ptr to base does not (can not) call the dtor of derived,
unless the dtor is virtual.
Jul 23 '05 #7

P: n/a
"tuvok" <52***************@t-online.de> wrote in message
news:d8*************@news.t-online.com

So, bottom line is: using ptr to base does not (can not) call the
dtor of derived, unless the dtor is virtual.


Yep.

--
John Carson
Jul 23 '05 #8

P: n/a

"Old Wolf" <ol*****@inspire.net.nz> wrote in message
news:11**********************@g43g2000cwa.googlegr oups.com...
Peter Julian wrote:
tuvok wrote:
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.


You are describing a non-virtual d~tor. Only D's d~tor would be
invoke. Which is the crux of the arguement of why a derived class
needs the base to have the virtual d~tor.


Please don't answer questions here if you don't know what
you are talking about. Invoking a derived class's destructor
ALWAYS calls the base class destructors.


He said "when D gets deleted". Please don't criticize my comments if you
can't even read the post. Incidentally, the base destructor isn't called,
its invoked. That means that you can't overide the base d~tor, in case you
are wondering what the difference is.

In the case a pointer to D is was involved, B's d~tor would not be invoked.

While my example didn't include a pointer to the derived class, the output
doesn't produce the warning.
Jul 23 '05 #9

P: n/a

"tuvok" <52***************@t-online.de> wrote in message
news:d8*************@news.t-online.com...
"Peter Julian" wrote

"tuvok" wrote in message
Is it correct that the virtual dtor of base gets called implicitly?
Not really, the virtual d~tor of base class is invoked, not called.
Here's some code to demonstrate what I mean:
Class B has a virtual destructor, so has class D which
is derived from B. Deleting D calls the dtor of D and
then the dtor of B.


B's d~tor is invoked and processed before D's d~tor can complete.
I was thinking that this would be true only for non-virtual dtor case,
but I wouldn't have expected it happen for a virtual dtor.
For a class with a virtual dtor I would have expected that only
the dtor of D would be called when D gets deleted.


You are describing a non-virtual d~tor. Only D's d~tor would be invoke.


No, it's not the case. Both ~D and ~B are invoked no matter whether
the dtors are virtual or not. So there seems no difference whether
the dtors are virtual or not. Ie. always the dtors of all parts get

invoked.


In the case where a pointer isn't involved, the base's d~tor will still be
invoked but you'll have the warning. You said "when D gets deleted". In the
case you had a pointer, something i didn't include in my example, your base
c~tor would not have been invoked.

Jul 23 '05 #10

P: n/a

"Peter Julian" <p_******@trap.trap.com> wrote in message
news:Rf*******************@news20.bellglobal.com.. .

"tuvok" <52***************@t-online.de> wrote in message
news:d8*************@news.t-online.com...
"Peter Julian" wrote
>
> "tuvok" wrote in message
>
> > Is it correct that the virtual dtor of base gets called implicitly?
>
> Not really, the virtual d~tor of base class is invoked, not called.
>
> > Here's some code to demonstrate what I mean:
> > Class B has a virtual destructor, so has class D which
> > is derived from B. Deleting D calls the dtor of D and
> > then the dtor of B.
>
> B's d~tor is invoked and processed before D's d~tor can complete.
>
> > I was thinking that this would be true only for non-virtual dtor
> > case,
> > but I wouldn't have expected it happen for a virtual dtor.
> > For a class with a virtual dtor I would have expected that only
> > the dtor of D would be called when D gets deleted.
>
> You are describing a non-virtual d~tor. Only D's d~tor would be invoke.


No, it's not the case. Both ~D and ~B are invoked no matter whether
the dtors are virtual or not. So there seems no difference whether
the dtors are virtual or not. Ie. always the dtors of all parts get

invoked.


In the case where a pointer isn't involved, the base's d~tor will still be
invoked but you'll have the warning. You said "when D gets deleted". In
the
case you had a pointer, something i didn't include in my example, your
base
c~tor would not have been invoked.


Eh? Of course the base class destructor is invoked! Whenever a derived
class is destroyed, the destructors for any base classes *must* be invoked,
whether you're using pointers or automatic variables. Otherwise, the memory
allocated for the base class portion(s) of the object would never get
returned to the system.

This is even true if the derived class object was assigned to a base class
pointer variable. The only difference in that case is that the base class
destructor needs to be virtual, or else the *derived* class destructor will
not get invoked.

There is no way for the destruction of the derived class to *not* also
invoke the destructor of the base class (aside from invoking undefined
behavior or abnormally terminating the process).

-Howard

Jul 23 '05 #11

P: n/a

"Howard" <al*****@hotmail.com> wrote in message
news:ZHire.947605$w62.229941@bgtnsc05-
In the case where a pointer isn't involved, the base's d~tor will still
be
invoked but you'll have the warning. You said "when D gets deleted". In
the
case you had a pointer, something i didn't include in my example, your
base
c~tor would not have been invoked.


"c~tor"???

You *did* mean "destructor" there, didn't you? I saw the ~, and missed the
"c" in front, but you were talking about destructors, so I'm assuming that's
what you meant. If you mean the "constructor", though, my argument is the
same...the base classes' constructor(s) must also be invoked, either
explicitly or implicitly, whenever a derived class it created, regardless of
whether you're using pointers or automatic variables.

-Howard
Jul 23 '05 #12

P: n/a

"Peter Julian" <p_******@trap.trap.com> skrev i en meddelelse
news:B9*******************@news20.bellglobal.com.. .

"Old Wolf" <ol*****@inspire.net.nz> wrote in message
news:11**********************@g43g2000cwa.googlegr oups.com...
Peter Julian wrote:
> tuvok wrote:
>> For a class with a virtual dtor I would have expected that only
>> the dtor of D would be called when D gets deleted.
>
> You are describing a non-virtual d~tor. Only D's d~tor would be
> invoke. Which is the crux of the arguement of why a derived class
> needs the base to have the virtual d~tor.
Please don't answer questions here if you don't know what
you are talking about. Invoking a derived class's destructor
ALWAYS calls the base class destructors.


He said "when D gets deleted". Please don't criticize my comments if you
can't even read the post. Incidentally, the base destructor isn't called,
its invoked. That means that you can't overide the base d~tor, in case you
are wondering what the difference is.

In the case a pointer to D is was involved, B's d~tor would not be
invoked.


This is plain rubbish. If D inherits from B, B's destructor will be invoked
when deleting a D-object. And this has nothing to do with whether a
destructor is virtual or not.


/Peter
Jul 23 '05 #13

P: n/a
tuvok wrote:
Is it correct that the virtual dtor of base gets called implicitly?


Yes. Let me reiterate to make sure you understand.

When an object is created, at the level of the most
derived object all the virtual bases are constructed
(in a depth first, left to right fashion). Then the
direct bases of the classes are constructed (in the
order listed in the class definition, not the mem-initializer
list), and then each non-static data member is constructed.
Then the constructor body of the object is run.

Each subobject above recursively constructs it's subobjects
(with the exception of avoiding duplicate construction of
the virtual bases).

There is nothing the program can do to change that ordering
(within defined behavior).
Objects are destructed in precisely the REVERSE ORDERING.

Virtualness of the destructor, arguments to the constructor,
etc... have no bearing on this behavior. It always happens
in the same topological order described above.
Jul 23 '05 #14

P: n/a

"Peter Koch Larsen" <pk*****@mailme.dk> wrote in message
news:It********************@news000.worldonline.dk ...

"Peter Julian" <p_******@trap.trap.com> skrev i en meddelelse
news:B9*******************@news20.bellglobal.com.. .

"Old Wolf" <ol*****@inspire.net.nz> wrote in message
news:11**********************@g43g2000cwa.googlegr oups.com...
Peter Julian wrote:
> tuvok wrote:
>> For a class with a virtual dtor I would have expected that only
>> the dtor of D would be called when D gets deleted.
>
> You are describing a non-virtual d~tor. Only D's d~tor would be
> invoke. Which is the crux of the arguement of why a derived class
> needs the base to have the virtual d~tor.

Please don't answer questions here if you don't know what
you are talking about. Invoking a derived class's destructor
ALWAYS calls the base class destructors.
He said "when D gets deleted". Please don't criticize my comments if you
can't even read the post. Incidentally, the base destructor isn't called, its invoked. That means that you can't overide the base d~tor, in case you are wondering what the difference is.

In the case a pointer to D is was involved, B's d~tor would not be
invoked.


This is plain rubbish. If D inherits from B, B's destructor will be

invoked when deleting a D-object. And this has nothing to do with whether a
destructor is virtual or not.


That was a typo or rather a mistake. I meant a base B pointer to D. As in...

int main(int argc, char* argv[])
{
B* p_d = new D;

delete p_d;

return 0;
}

Jul 23 '05 #15

P: n/a

"Howard" <al*****@hotmail.com> wrote in message
news:ZH*********************@bgtnsc05-news.ops.worldnet.att.net...

"Peter Julian" <p_******@trap.trap.com> wrote in message
news:Rf*******************@news20.bellglobal.com.. .

"tuvok" <52***************@t-online.de> wrote in message
news:d8*************@news.t-online.com...
"Peter Julian" wrote
>
> "tuvok" wrote in message
>
> > Is it correct that the virtual dtor of base gets called implicitly?
>
> Not really, the virtual d~tor of base class is invoked, not called.
>
> > Here's some code to demonstrate what I mean:
> > Class B has a virtual destructor, so has class D which
> > is derived from B. Deleting D calls the dtor of D and
> > then the dtor of B.
>
> B's d~tor is invoked and processed before D's d~tor can complete.
>
> > I was thinking that this would be true only for non-virtual dtor
> > case,
> > but I wouldn't have expected it happen for a virtual dtor.
> > For a class with a virtual dtor I would have expected that only
> > the dtor of D would be called when D gets deleted.
>
> You are describing a non-virtual d~tor. Only D's d~tor would be invoke.
No, it's not the case. Both ~D and ~B are invoked no matter whether
the dtors are virtual or not. So there seems no difference whether
the dtors are virtual or not. Ie. always the dtors of all parts get invoked.


In the case where a pointer isn't involved, the base's d~tor will still be invoked but you'll have the warning. You said "when D gets deleted". In
the
case you had a pointer, something i didn't include in my example, your
base
c~tor would not have been invoked.


Eh? Of course the base class destructor is invoked! Whenever a derived
class is destroyed, the destructors for any base classes *must* be

invoked, whether you're using pointers or automatic variables. Otherwise, the memory allocated for the base class portion(s) of the object would never get
returned to the system.

This is even true if the derived class object was assigned to a base class
pointer variable. The only difference in that case is that the base class
destructor needs to be virtual, or else the *derived* class destructor will not get invoked.

There is no way for the destruction of the derived class to *not* also
invoke the destructor of the base class (aside from invoking undefined
behavior or abnormally terminating the process).

-Howard


I meant a Base * to a new D. My mistake. Its been a long day.

Jul 23 '05 #16

P: n/a

"Ron Natalie" <ro*@spamcop.net> wrote in message
news:42***********************@news.newshosting.co m...
tuvok wrote:
Is it correct that the virtual dtor of base gets called implicitly?


Yes. Let me reiterate to make sure you understand.

When an object is created, at the level of the most
derived object all the virtual bases are constructed
(in a depth first, left to right fashion). Then the
direct bases of the classes are constructed (in the
order listed in the class definition, not the mem-initializer
list), and then each non-static data member is constructed.
Then the constructor body of the object is run.

Each subobject above recursively constructs it's subobjects
(with the exception of avoiding duplicate construction of
the virtual bases).

There is nothing the program can do to change that ordering
(within defined behavior).
Objects are destructed in precisely the REVERSE ORDERING.

Virtualness of the destructor, arguments to the constructor,
etc... have no bearing on this behavior. It always happens
in the same topological order described above.


I just wrote a program and compiled and ran to test this theory, and it
seems
that "Objects are destructed in precisely the REVERSE ORDERING" is
not always true. Here is the program:

#include <iostream>

class base
{
public:
int i;
base() { std::cout << "b ctor" << std::endl; }
~base() { std::cout << "b dtor" << std::endl; }
};

class derived : public base
{
public:
derived() { std::cout << "d ctor" << std::endl; }
~derived() { std::cout << "d dtor" << std::endl; }
};

int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;

std::cout << std::endl;

d = new derived;
delete d;

char c;
std::cin >> c;

return 0;

}

And it's Output:

b ctor
d ctor
b dtor

b ctor
d ctor
d dtor
b dtor

As you can see, the derived dtor was NOT called when the derived was
instatized to a base pointer.

Change the base dtor to:

produces this output:
b ctor
d ctor
d dtor
b dtor

b ctor
d ctor
d dtor
b dtor

Where the derived dtor is called in both instances.

But, yes, the base dtor does get called in either case either.
Jul 23 '05 #17

P: n/a
"Jim Langston" <ta*******@rocketmail.com> wrote in message
news:4%***************@fe07.lga...

Where the derived dtor is called in both instances.
virtual ~base() { std::cout << "b dtor" << std::endl; }
But, yes, the base dtor does get called in either case either.


(Sorry, left out that one line)
Jul 23 '05 #18

P: n/a
Jim Langston wrote:
Each subobject above recursively constructs it's subobjects
(with the exception of avoiding duplicate construction of
the virtual bases).

There is nothing the program can do to change that ordering
(within defined behavior).
Objects are destructed in precisely the REVERSE ORDERING.

I just wrote a program and compiled and ran to test this theory, and it
seems
that "Objects are destructed in precisely the REVERSE ORDERING" is
not always true. Here is the program:

I was referring to the order of destruction of subobjects in
an object.
Jul 23 '05 #19

P: n/a
Jim Langston wrote:

int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;

This is UNDEFINED BEHAVIOR... your program is incorrect
and there is no point in even conjecture as to what
the observable behavior is.

It has no bearing on the original problem or my answer.
Jul 23 '05 #20

P: n/a

"Ron Natalie" <ro*@spamcop.net> wrote in message
news:42**************@spamcop.net...
Jim Langston wrote:

int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;

This is UNDEFINED BEHAVIOR... your program is incorrect
and there is no point in even conjecture as to what
the observable behavior is.

It has no bearing on the original problem or my answer.


What part of it is undefined behavior? AFAIK everything I did in my
program follows ANSI C and the behavior that resulted. If I'm doing
something undefined I wanna know what it is so I won't do it anymore.
Jul 23 '05 #21

P: n/a
Jim Langston <ta*******@rocketmail.com> wrote:
|
| "Ron Natalie" <ro*@spamcop.net> wrote in message
| news:42**************@spamcop.net...
| > Jim Langston wrote:
| >
| >>
| >> int _tmain(int argc, _TCHAR* argv[])
| >> {
| >> base* b;
| >> derived* d;
| >>
| >> b = new derived;
| >> delete b;
| >>
| > This is UNDEFINED BEHAVIOR... your program is incorrect
| > and there is no point in even conjecture as to what
| > the observable behavior is.
| >
| > It has no bearing on the original problem or my answer.
|
| What part of it is undefined behavior? AFAIK everything I did in my
| program follows ANSI C and the behavior that resulted. If I'm doing
| something undefined I wanna know what it is so I won't do it anymore.

From § 5.3.5.3 (about delete expressions):
if the static type of the operand is different from its dynamic type,
the static type shall be a base class of the operands dynamic type
and the static type shall have a virtual destructor or the behavior
is undefined.

Since the static type of *b is base, and the dynamic is derived, base
ought to have a virtual destructor. Btw: This is from the C++ standard,
not C.
--
Robert Bauck Hamar
Jul 23 '05 #22

P: n/a
Jim Langston wrote:
"Ron Natalie" <ro*@spamcop.net> wrote in message
news:42**************@spamcop.net...
Jim Langston wrote:

int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;


This is UNDEFINED BEHAVIOR... your program is incorrect
and there is no point in even conjecture as to what
the observable behavior is.

It has no bearing on the original problem or my answer.

What part of it is undefined behavior? AFAIK everything I did in my
program follows ANSI C and the behavior that resulted. If I'm doing
something undefined I wanna know what it is so I won't do it anymore.

Deleting a derived object through a pointer to a base class is undefined
behavior when the base class doesn't have a virtual destructor.
Jul 23 '05 #23

P: n/a
On 2005-06-15 18:15:30 -0400, "Jim Langston" <ta*******@rocketmail.com> said:

"Ron Natalie" <ro*@spamcop.net> wrote in message
news:42**************@spamcop.net...
Jim Langston wrote:

int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;
This is UNDEFINED BEHAVIOR... your program is incorrect
and there is no point in even conjecture as to what
the observable behavior is.

It has no bearing on the original problem or my answer.


What part of it is undefined behavior?

I notice two things:

1) The name "_tmain", if in the global namespace, is reserved for implementors.
2) If base does not have a virtual destructor, then "delete b" is UB.

AFAIK everything I did in my program follows ANSI C and the behavior that resulted.
I hope that you meant ANSI C++ there :)

If I'm doing something undefined I wanna know what it is so I won't
do it anymore.

--
Clark S. Cox, III
cl*******@gmail.com

Jul 23 '05 #24

P: n/a
> That was a typo or rather a mistake. I meant a base B pointer to D. As
in...

int main(int argc, char* argv[])
{
B* p_d = new D;

delete p_d;

return 0;
}


Following your arguments: you are wrong.
You said, "You are describing a non-virtual d~tor. Only D's d~tor would be
invoke."

You know what the standard says ?
It says that it is UNDEFINED.
That means you cannot conclude "Only D's d~tor would be invoke." if B lacks
a virtual destructor and you have the above code.
Anything is legitimate.
It may well be that on your implementation that only D's dtor is invoked but
that is just _THAT_ implementation.

SH
Jul 23 '05 #25

P: n/a
> ..., or else the *derived* class destructor will not get invoked.

"Or else" nothing. It is undefined behaviour according to C++ standard.
Nothing can be concluded as to how it behaves.

SH
Jul 23 '05 #26

P: n/a

"Clark S. Cox III" <cl*******@gmail.com> wrote in message
news:2005061519100450073%clarkcox3@gmailcom...
On 2005-06-15 18:15:30 -0400, "Jim Langston" <ta*******@rocketmail.com>
said:

"Ron Natalie" <ro*@spamcop.net> wrote in message
news:42**************@spamcop.net...
Jim Langston wrote:
int _tmain(int argc, _TCHAR* argv[])
{
base* b;
derived* d;

b = new derived;
delete b;

This is UNDEFINED BEHAVIOR... your program is incorrect
and there is no point in even conjecture as to what
the observable behavior is.

It has no bearing on the original problem or my answer.
What part of it is undefined behavior?

I notice two things:

1) The name "_tmain", if in the global namespace, is reserved for
implementors.


Ahh, well, I simply let M$ VC++ .net 2003 create a console program for me
and
threw in the code, cimpiled and ran. I didnt' think to check how it mangled
main. My bad.
2) If base does not have a virtual destructor, then "delete b" is UB.
So, then, if I *always* give a base class that is going to have derived
classes a virtual
destructor then I"ll be in ANSI compliance and DB. Good to know. I"ll try
to make sure
I use virtual dtors on base classes.
AFAIK everything I did in my
program follows ANSI C and the behavior that resulted.

I hope that you meant ANSI C++ there :)


Yeah, I did. Type there.

Thanks for the info.
Jul 23 '05 #27

P: n/a

"Stephen Howe" <sjhoweATdialDOTpipexDOTcom> wrote in message
news:42*********************@news.dial.pipex.com.. .
..., or else the *derived* class destructor will not get invoked.


"Or else" nothing. It is undefined behaviour according to C++ standard.
Nothing can be concluded as to how it behaves.

SH


Sorry, you're correct. It's undefined behavior.
-Howard
Jul 23 '05 #28

This discussion thread is closed

Replies have been disabled for this discussion.