The results of the following code are inferred from the test:
#include <stdio.h> #include <stdlib.h> #include <exception>using namespace std;void* operator new ( size_t size) {printf ("My New,%u\n", size); return malloc (size);} void operator delete (void *p) {printf ("mydelete\r\n"); return free (p);} Class A{public:a () {printf ("a\n"); throw int (-1);} ~a () {printf ("~a\n");}}; int main () {A * p = null;try{p = new A;} catch (int& i) {printf ("exception-%d\n", i);} return 0;}
To know the output of the above code, you might want to know what the C + + new is doing, and how C + + handles the situation if the destructor throws an exception.
In fact, the output of the above code is:
1Amydeleteexception, my new-1
In fact, when you new an object, C + + first needs to allocate memory for the object before it calls the object's destructor, and C + + calls the new (sizeof (T)) function to allocate memory. The approximate process is as follows:
The new actual process is roughly: A * p = (A *) malloc (sizeof (A)); Try{a ();} catch (...) {//Guaranteed no memory leaks after exception//no destructors are called (objects are not created successfully, destructor is meaningless) delete P;throw exception;}
In addition, when a constructor is found to throw an exception in the new procedure and the constructor fails to handle the exception, C + + causes the object's creation to fail and frees the allocated memory, but it is important to note that C + + does not remove the destructor of the object.
So by the above knowledge we can analyze the output of the above code concretely.
Therefore, for a constructor that throws an exception, we can do the following analysis:
#include <stdio.h> #include <stdlib.h> #include <exception>using namespace std;//heavy newvoid* operator New (size_t size) {printf ("My New,%u\n", size); return malloc (size);} Reload deletevoid operator delete (void *p) {printf ("mydelete\r\n"); return free (p);} Class A{public:a () {printf ("a\n");//The destructor throws an exception//C + + automatically frees allocated memory but does not call the destructor throw int (-1);} ~a () {printf ("~a\n");//destructor is not recommended to throw an exception, if must, to self-implement exception handling}};int main () {A * p = null;try{//here actually calls operator new (sizeof (A))// If the constructor throws an exception, the return value of new is NULLP = new A;} catch (int& i) {printf ("exception-%d\n", i);} return 0;}
Constructor throws an exception