Two pointer to the same object - c++

I have two pointers which points to the same object and I need to delete them correctly (delete each object A and the inner object B). But the problem is that the shared object still have memory allocated after delete: A dangling pointer. How can I avoid such a problem without using smart pointer.
class A
{
public:
class B
{
private:
A* m_x;
A* m_y;
public:
B(A* x, A* y);
~B();
};
B* m_b;
A(){};
void Join(A* other);
~A();
};
void A::Join(A* person)
{
this->m_b= new A::B(this, person);
person->m_b= this->m_b;
}
A::~A()
{
if (m_b)
{
delete m_b;
m_b= NULL;
}
}
...
A aa = new A();
A cc = new A();
aa->Join(cc);
delete aa
// here I have a problem in deleting the *m_b because it's deleted by the first A
delete cc;

Without smart pointers, the best you could do is disjoin your aa and cc at destruction time. But don't do this, use std::shared_ptr and forget about similar headaches:
// annul pointers to this shared object
B::detach() {
if (m_x) m_x->m_b = NULL;
if (m_y) m_y->m_b = NULL;
}
A::~A() {
// use a temporary pointer, because B::detach will annul the pointers here
if (m_b) {
B* tmp = m_b;
tmp->detach();
delete tmp;
}
}
Such code is very bad. It is unmaintainable, the classes are coupled, and I am not even sure if it is correct.

Related

Vector of custom class contained pointer of other class

I am writing a short code with vector which element are custom class objects.
The custom class also contained a pointer to another class.
The memory of b_ptr were freed after delete aPtr in main process cause it only copy the pointer(not stored data) when push_back object to vector.
Any idea to solve this?
(*shared_ptr is not able to use in my system.)
Thanks~
struct myStruct
{
vector<uint16_t> pers;
vector<string> strs;
};
class A
{
A(){ b_ptr = new B() };
B* b_ptr;
};
class B
{
B();
vector<myStruct> mStruct;
};
And main process as below
main()
{
vector<A> v_of_a;
A* aPtr;
while(something != NULL)
{
aPtr = new A();
//Handling with data for property of A, vector data of B
v_of_a.push_back(*aPtr);
delete aPtr;
}
}
If I understand your question correctly, you're asking "how do I get the memory pointed to by b_ptr to be deallocated when the A instance is?
To do this, you need to use a destructor:
struct A {
A() {
b_ptr = new B();
}
~A() {
delete b_ptr;
}
B* b_ptr;
};

how to create object on 1>stack only and not on heap and 2>heap only not on stack

To create object on heap only->
1>is there anything wrong in the code
class B
{
~B(){}
public:
void Destroy()
{
delete this;
}
};
int main() {
B* b = new B();
b->Destroy();
return 0;
}
why you cant create object of class b on stack
2>
class B
{
B(){}
public:
static B* Create()
{
return new B();
}
};
int main() {
//B S;
B* b = B::Create();
return 0;
}
3>how to create object only on stack and not on heap
If you want to create object only in Heap make destructor as private. Once the destructor is made Private, the code will give compiler error in case on object creation on stack. If you do not use new the object will be created on stack.
1) Object creation only on Heap
class B
{
~B(){}
public:
void Destroy()
{
delete this;
}
};
int main() {
B* b = new B();
b->Destroy();
return 0;
}
Nothing seems to be wrong with above code, If you try to create the object on stack B b1 it will give compiler error.
2) For restricting the object creation on heap, Make operator new as private.
You code
class B
{
B(){}
public:
static B* Create()
{
return new B();
}
};
int main() {
//B S;
B* b = B::Create();
return 0;
}
This code is still creating object on Heap/Free store as it is using new.
3) To create object only on stack not on heap, the use of new operator should be restricted. This can be achieved making operator new as private.
class B
{
Private:
void *operator new(size_t);
void *operator new[](size_t);
};
int main() {
B b1; // OK
B* b1 = new B() ; // Will give error.
return 0;
}
Look at Concrete Data Type idiom: To control object's scope and lifetime by allowing or disallowing dynamic allocation using the free store (heap)

An error on delete a 2D array in class

I'm designing a class that's wrapper of a 2D array. Anything seems ok, except the destruction function. I don't know why it throws an access violent reading.
I have tried to detect what happened and I still can't solve this problem. I need your help. Thank you.
class ClassA
{
int Num;
public:
ClassA()
{}
~ClassA(void)
{}
};
class ClassB
{
ClassA* pA;
public:
ClassB()
{}
ClassB(ClassA obj)
{
pA = new ClassA[1];
pA[0] = obj;
}
~ClassB(void)
{
delete[] pA;
}
ClassB::ClassB(ClassB& src)
{
this->~ClassB();
pA = new ClassA[1];
pA[0] = src.pA[0];
}
ClassB& ClassB::operator =(const ClassB& src)
{
if (this == &src)
return *this;
this->~ClassB();
pA = new ClassA[1];
pA[0] = src.pA[0];
return (*this);
}
};
ClassB Test5()
{
ClassA A;
ClassB B( A );
return B;
}
void Test6()
{
ClassB B;
B = Test5();
}
The exception will be thrown after finishing of Test6 function.
Get out of the habit of explicitly calling destructors. Such an act does not reinitialise the object or its (non-static) members - it logically destroys the object so it cannot be used.
this->~ClassB() makes any attempt to access non-static members of the current object (i.e. *this) give undefined behaviour.
For example, in the copy constructor of ClassB
ClassB::ClassB(ClassB& src)
{
this->~ClassB();
pA = new ClassA[1];
pA[0] = src.pA[0];
}
the accesses of pA in the last two statements are (implicitly) this->pA. So they both have undefined behaviour.
There are circumstances where explicitly calling a destructor is appropriate. But assignment operators and copy constructors are generally not among those circumstances.

C++ Function Returning Pointer to Dynamically Allocated Object

I have two Class A and B.
class B
{
};
class A
{
public:
B* CreateB( void )
{
B* obj = new B();
return obj;
}
}
When the client calls A::CreateB(), it has to delete the returned B* pointer even it does not know the underlying implementation. Is there any way to avoid this? Any suggestion is appreciated.
First, you should use Constructor and Destructor, the following code:
But, this method is not recommended! You should read the book -- effective c++
class B
{
};
class A
{
public:
A()
{
obj = new B();
}
~A()
{
if (obj)
{
delete obj;
}
}
B* obj;
};
second, you should use smart pointer, the following code:
class B
{
};
class A
{
public:
std::shared_ptr<B> CrteateB( void )
{
std::shared_ptr<B> obj(new B);
return obj;
}
};

Scalar deleting destructor

I have a piece of code (from a DLL) that looks like this:
class A {
public:
virtual ~A();
};
class B : public A {
public:
~B();
}
~A() {
// #1
}
~B() {
// #2
}
When I use delete an_instance_of_B I get scalar deleting destructor. Any workarounds?
Don't delete an instance of B. You're supposed to use delete on pointers to object allocated with new:
B b;
delete b; //wrong
//.........
B* pB = new pB;
delete pB; //okay
//.........
B justThis; //best