operator new question | | |
hello,
When we use new operator to user defined type, constructor will be called
and a memory block is created in heap. My question: where those non-pointer
data members belonging to this user-defined class will be create? on heap or
on stack? Obviousely it's on heap.
OK, if it's on heap, how stack unwinding meachnism can destroy those data
members when exception happened? Since it's not on stack, it's on heap!
I read the c++ progamming language by BStroustrup and can not find the
answer, please help understanding. Thanks very much!
John | | | | re: operator new question
"john sun" <johnsun@sbcglobal.net> skrev i en meddelelse
news:E78Nb.8793$y52.6479@newssvr16.news.prodigy.co m...[color=blue]
> hello,
>
> When we use new operator to user defined type, constructor will be called
> and a memory block is created in heap. My question: where those[/color]
non-pointer[color=blue]
> data members belonging to this user-defined class will be create? on heap[/color]
or[color=blue]
> on stack? Obviousely it's on heap.
>
> OK, if it's on heap, how stack unwinding meachnism can destroy those data
> members when exception happened? Since it's not on stack, it's on heap!
>
> I read the c++ progamming language by BStroustrup and can not find the
> answer, please help understanding. Thanks very much!
>
> John
>
>[/color]
Well..... all members of the object will be stored in the heap, regardless
of whether they are pointers or not. Also, a pointer has no destructor so
nothing happens if it leaves scope:
class C {...};
void test()
{
C c_stack;
C* c_ptr = new C();
if (...)
throw 0;
}
When test returns (or throws), the destructor of c_stack will be called.
c_ptr is not an object (it is a plain pointer) so there will be a memory
leak and a live object somewhere, possible holding on to other ressources.
In short, only use pointer variables when you want to create an object with
a scope reaching outside the point, where it is created. Also in those cases
you should wrap the pointer in a smart-pointer class such as the ones you
can find at boost.
Kind regards
Peter Koch Larsen | | | | re: operator new question
"john sun" <johnsun@sbcglobal.net> wrote in message news:E78Nb.8793$y52.6479@newssvr16.news.prodigy.co m...[color=blue]
> hello,
>
> When we use new operator to user defined type, constructor will be called
> and a memory block is created in heap. My question: where those non-pointer
> data members belonging to this user-defined class will be create? on heap or
> on stack? Obviousely it's on heap.[/color]
The non-static members (pointer or otherwise) will be created with the object
(i.e., on the heap). Don't confuse a pointer with the object it points to. If
there is a member that is a pointer, then the object it points to is whatever the
class sets it to. | | | | re: operator new question
john sun wrote:
[color=blue]
> hello,
>
> When we use new operator to user defined type, constructor will be
> called and a memory block is created in heap.[/color]
Yes, though the C++ standard doesn't actually call it heap.
[color=blue]
> My question: where those
> non-pointer data members belonging to this user-defined class will be
> create? on heap or on stack? Obviousely it's on heap.[/color]
Yes.
[color=blue]
> OK, if it's on heap, how stack unwinding meachnism can destroy those
> data members when exception happened? Since it's not on stack, it's on
> heap![/color]
Stack unwinding doesn't have anything to do with dynamically allocated
objects. It rather destroys the local variables of a function when an
exception occurs during that function. | | | | re: operator new question
"john sun" <johnsun@sbcglobal.net> wrote in message
news:E78Nb.8793$y52.6479@newssvr16.news.prodigy.co m...[color=blue]
> hello,
>
> When we use new operator to user defined type, constructor will be called
> and a memory block is created in heap. My question: where those[/color]
non-pointer[color=blue]
> data members belonging to this user-defined class will be create? on heap[/color]
or[color=blue]
> on stack? Obviousely it's on heap.
>
> OK, if it's on heap, how stack unwinding meachnism can destroy those data
> members when exception happened? Since it's not on stack, it's on heap!
>[/color]
Put something on the stack that will delete it for you.
Have a look at std::auto_ptr.
void f()
{
auto_ptr<T> p = new T;
if( error )
throw "error";
}
However the function exits the T will be deleted.
[color=blue]
> I read the c++ progamming language by BStroustrup and can not find the
> answer, please help understanding. Thanks very much!
>
> John
>
>[/color] | | | | re: operator new question
here is example:
#include "stdafx.h"
#include <stdio.h>
#include <memory>
using namespace std;
class O
{
public:
O(){};
~O(){};
}
;
class A1
{
O* o;
public :
A1()
{
o=new O();
printf("in A1 ctor\n");
}
~A1()
{
delete o;
printf("in A1 dtor\n");
};
};
class A
{
public :
A(){printf("in A ctor\n");};
~A(){printf("in A dtor\n");};
};
class B
{
auto_ptr<A> a;
A1 a1;
public:
B():a(new A)
{
throw 1;
}
~B(){printf("in B dtor\n");}
};
int main(int argc, char* argv[])
{
try{
B *b=new B();
}
catch(int)
{
printf("catch block\n");
}
return 0;
}
After running a1 and a destructor will be called. This confused me. Since b
is created in heap, and a and a1 is also on heap, how come exception can
call a1 and a's destructor.
Thanks for furthermore clarifying.
Best regards to all! | | | | re: operator new question
Fortunately
[color=blue]
> After running a1 and a destructor will be called. This confused me. Since b
> is created in heap, and a and a1 is also on heap, how come exception can
> call a1 and a's destructor.
>[/color]
First, there is the concept of a "fully constructed object". An object is
fully constructed when its constructor body has been run. When an exception
happens during object creation, all the things that are fully constructed get
their destructors run.
In this case what happens when you call new B:
1. sizeof(B) bytes is allocated by the global operator new.
2. B's subobjects are constructed. B::a is constructed by dynamically
creating an A object (I'll omit the details of this) dynamically and feeding
it to the auto_ptr constructor. B::a is now fully constructed at this point.
3. B::a1 is default constructed. B::a1 is now fully constructed.
4. The constructor body of B is run.
5. The throw expression is encountered.
6. The compiler now destructs all of the fully constructed parts of B in reverse order:
B::a1 is destroyed.
7. B::a is destroyed, the auto_ptr destructor deletes the referenced A object.
8. The global operator delete is called to return the memory used by B.
9. The stack is unwound up to the point where the handler is found... and control
is transferred there. | | | | re: operator new question
Thanks Ron!
I know those steps, I am confused the fully constructed object could be
destructed. Since those fully constructed object is on the heap in my
example. If you say fully constructed object can be destructed there should
be some limitations. Because the following code also demo the fully
constructed object will not be destroyed.
class A{};
void foo()
{
A * a=new A();
throw 1;
return 0;
}
int main{
try {
foo();
}
catch(...)
{};
return 0;
}
Object pointed by a will not be deleted even it's a fully constructed
object. I know because c++ lost track of a pointed object. But why in our
previous example, the sub object which is also created on heap will be
deleted if exception throw? Looks like to me c++ can track the subobject
what even it's created on heap or stack. What's the mechanism here?
Thanks very much for sharing and insightful discussion
John
"Ron Natalie" <ron@sensor.com> wrote in message
news:40057d99$0$71356$9a6e19ea@news.newshosting.co m...[color=blue]
> Fortunately
>[color=green]
> > After running a1 and a destructor will be called. This confused me.[/color][/color]
Since b[color=blue][color=green]
> > is created in heap, and a and a1 is also on heap, how come exception can
> > call a1 and a's destructor.
> >[/color]
> First, there is the concept of a "fully constructed object". An object[/color]
is[color=blue]
> fully constructed when its constructor body has been run. When an[/color]
exception[color=blue]
> happens during object creation, all the things that are fully constructed[/color]
get[color=blue]
> their destructors run.
>
> In this case what happens when you call new B:
>
> 1. sizeof(B) bytes is allocated by the global operator new.
> 2. B's subobjects are constructed. B::a is constructed by dynamically
> creating an A object (I'll omit the details of this) dynamically and[/color]
feeding[color=blue]
> it to the auto_ptr constructor. B::a is now fully constructed at[/color]
this point.[color=blue]
> 3. B::a1 is default constructed. B::a1 is now fully constructed.
> 4. The constructor body of B is run.
> 5. The throw expression is encountered.
> 6. The compiler now destructs all of the fully constructed parts of B in[/color]
reverse order:[color=blue]
> B::a1 is destroyed.
> 7. B::a is destroyed, the auto_ptr destructor deletes the referenced A[/color]
object.[color=blue]
> 8. The global operator delete is called to return the memory used by B.
> 9. The stack is unwound up to the point where the handler is found... and[/color]
control[color=blue]
> is transferred there.
>[/color] | | | | re: operator new question
"john sun" <johnsun@sbcglobal.net> wrote in message
news:t1nNb.57000$DO3.27519@newssvr31.news.prodigy. com...[color=blue]
> Thanks Ron!
>
> I know those steps, I am confused the fully constructed object could be
> destructed. Since those fully constructed object is on the heap in my
> example. If you say fully constructed object can be destructed there[/color]
should[color=blue]
> be some limitations. Because the following code also demo the fully
> constructed object will not be destroyed.
>
> class A{};
>
> void foo()
> {
> A * a=new A();[/color]
replace with "std::auto_ptr<A> a = new A; " and it will be destructed.
- A* is a pointer which has no destructor.
- std::auto_ptr<A> is an object with a defined destructor that, when called,
calls delete on the pointer it holds
[color=blue]
> throw 1;
> return 0;
> }
>
> int main{
> try {
> foo();
> }
> catch(...)
> {};
> return 0;
> }
>[/color] |  | | | | /bytes/about
We are a network of experts and professionals in IT and software development that help one another with answers to tough questions and share insights.
Get the best answers to your questions from over 226,537 network members.
|