C++ Exception: Why does this program behave differently for pointer and array of pointer

D

Divick

Hi,
can somebody please help me figure out what is wrong with the
following program? If I run this program, then the destructor for the
first pointer in the array is called because exception occurs as soon
as it tries to allocate the second pointer in the array but the
destructor for the pointers a1 and a2 are not called.

Does any one have answers ?
Thanks in advance,
Divick

#include <exception>
#include <iostream>
using namespace std;

class A
{
static int count;
int id;
public:
A() throw(int)
{
id = count;
count++;
cout << "Inside A's constructor object id " << is->>id <<
endl;
if(id==3)
throw 0;
}
virtual ~A()
{
cout << "Inside A's destructor for object id " <<
this->>id << endl;
}
};
int A::count = 0;
int main(){
try{
A * a1 = new A();
A * a2 = new A();
A * array = new A[3];
cout < < "Exiting try" << endl;
}catch(...){
cout << "Inside catch..." << endl;
}
}
 
J

John Harrison

Divick said:
Hi,
can somebody please help me figure out what is wrong with the
following program? If I run this program, then the destructor for the
first pointer in the array is called because exception occurs as soon
as it tries to allocate the second pointer in the array but the
destructor for the pointers a1 and a2 are not called.

Does any one have answers ?

OK you are under a serious misapprehension about C++. There are no
destructors for pointers in C++. Simple as that. This one thing that
what makes pointers so difficult to handle correctly.

When an exception is thrown in a constructor, then if the constructor
was being used in a new operator then the memory for that operation will
be freed (because there would be no other way to free it), but any other
allocated memory is your responsibility to free.

john
 
I

Ian

Divick said:
Hi,
can somebody please help me figure out what is wrong with the
following program? If I run this program, then the destructor for the
first pointer in the array is called because exception occurs as soon
as it tries to allocate the second pointer in the array but the
destructor for the pointers a1 and a2 are not called.

Does any one have answers ?

Dynamic objects don't get destroyed when they go out of scope, you have
to use delete. You see the first element in the array (which is an A,
not a pointer to A) being destroyed.

Ian

PS, you don't have to type this->.
 
D

Divick

Hi John,
thanks for you prompt reply. Yes I understand that there
is no constructor/destructor for pointers in C++ actually what I meant
was constructor of the class to whose' instance this pointer points (
didn't write so explicitly to avoid confusion and it was implicit).
Regarding your answer, do you mean that in the creation of
A * array = new A[3];
the new is implicitly called by the operator [], which allocates three
instances of class A and hence the destructor will also be called for
it, while in case of simple pointer allocation A * a = new A(); since
new is called by me and hence I will need to delete ?

Thanks,
Divick
 
J

John Harrison

Divick said:
Hi John,
thanks for you prompt reply. Yes I understand that there
is no constructor/destructor for pointers in C++ actually what I meant
was constructor of the class to whose' instance this pointer points (
didn't write so explicitly to avoid confusion and it was implicit).
Regarding your answer, do you mean that in the creation of
A * array = new A[3];
the new is implicitly called by the operator [], which allocates three
instances of class A and hence the destructor will also be called for
it, while in case of simple pointer allocation A * a = new A(); since
new is called by me and hence I will need to delete ?

No I didn't mean that. In both cases you must explicitly call delete
(actually you must call delete[] for the first case).

However your original question was actually about what happens when a
constructor throws an exception. Ian pointed out the correct answer (I
think he understood exactly what you were asking a bit better than me).

If you write

A* a = new A[3];

then the constructor for A will be called three times (normally). If the
second call to the constructor throws an exception then (a) the third
constructor call won't happen, and (b) the destructor for the first
constructed object will be called, (c) the memory allocated by new will
be freed.

This should be exactly what you want to happen, because it means you
don't have to do any cleanup yourself. All the objects that were
cnostructed have been destroyed, and all the memory that was allocated
has been freed.

john
 
J

John Harrison

Maybe your fundamental misunderstanding is that

A* a = new A[3];

is *not* an array of pointers. (Sorry I didn't read the full subject of
your post).

This is an array of pointers

A** a = new A*[3];

Try that, and see what behaviour you get.

john
 
D

Divick

Thanks for the answer. I use this-> to make it more explicit (probably
a good programming practise). :)

Divick
 
D

Divick

John, Ian thanks for your answers. Similar answers from several people
in lang.c++.moderated list. See my post on moderated list with the same
title.

Thanks
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
474,432
Messages
2,571,680
Members
48,796
Latest member
Greg L.

Latest Threads

Top