one more question with smart_ptr

T

toton

Hi,
One more question with smart_ptr ( I am using the one from Axter).
I want to assign the object to the pointer later, not at the
construction time.
like,
smart_ptr<Base> pBase;
///what will be the step here to release the NULL pointer and reduce
the reference count?
pBase = smart_ptr<Base>(new Derived()) ; ///???
Here upon deletion it deletes the Derived twice. Thus I want pBase to
point nowhere and when only it is assigned, the count to increase.

I want it, in case, when the exact derived class is calculated after
some computation, inside constructor (Not in initializer list) and
assigned later.
To give an idea, say the code is a builder like,

class DerivedBuilder{
private:
smart_ptr<Base> pBase;
public:
DerivedBuilder(int type){
if(type < =0) {
pBase = smart_ptr<Base>(new Derived1()) ;
}
else if(type > 0 & <=10){
pBase = smart_ptr<Base>(new Derived3()) ;
}
else{
pBase = smart_ptr<Base>(new Derived2()) ;
}
}
};

Here it is synonymous to boost shared_ptr. I want pBase will call the
destructor only once.
Thanks
abir
 
M

mlimber

toton said:
One more question with smart_ptr ( I am using the one from Axter).
I want to assign the object to the pointer later, not at the
construction time.
like,
smart_ptr<Base> pBase;
///what will be the step here to release the NULL pointer and reduce
the reference count?
pBase = smart_ptr<Base>(new Derived()) ; ///???
Here upon deletion it deletes the Derived twice. Thus I want pBase to
point nowhere and when only it is assigned, the count to increase.

No. With any smart pointer that is worthy of the name (e.g.,
std::tr1::shared_ptr, std::auto_ptr, etc.), you don't need to do
anything. The smart pointer will initialize to null (and the reference
count, if there is one, will be 0), and since it's safe to delete a
null pointer
(http://parashift.com/c++-faq-lite/freestore-mgmt.html#faq-16.8), the
normal reassignment procedure should work fine.

Cheers! --M
 
T

toton

mlimber said:
No. With any smart pointer that is worthy of the name (e.g.,
std::tr1::shared_ptr, std::auto_ptr, etc.), you don't need to do
anything. The smart pointer will initialize to null (and the reference
count, if there is one, will be 0), and since it's safe to delete a
null pointer
(http://parashift.com/c++-faq-lite/freestore-mgmt.html#faq-16.8), the
normal reassignment procedure should work fine.
If I write
auto_ptr<Base> pBase;
pBase = auto_ptr<Base>(new Derived(5));

I get the expected result. Derived destructor & Base destructor is
called only once.

However If I use Axter smart_ptr (which is pretty common and has its
origin on Andrei Alexandrescu 's policy based smart pointers ),
smart_ptr<Base> pBase1;
pBase1 = smart_ptr<Base>(new Derived(5));
I get the destructor gets called twice. For a single line statement it
works fine.
can anyone point to the problem. The Base and Derived class are simple,
just to track emmory, has a cout in ctor and dtor.

Thanks
 
K

Kai-Uwe Bux

toton said:
Hi,
One more question with smart_ptr ( I am using the one from Axter).
I want to assign the object to the pointer later, not at the
construction time.
like,
smart_ptr<Base> pBase;
///what will be the step here to release the NULL pointer and reduce
the reference count?
pBase = smart_ptr<Base>(new Derived()) ; ///???
Here upon deletion it deletes the Derived twice. Thus I want pBase to
point nowhere and when only it is assigned, the count to increase.

Are you using the copy_ptr or clone_ptr policies? In that case, there would
be no reference count. Instead each pointer has its own unique pointee and
upon pointer-assignments, such pointees get deep-copied. Thus, when you see
a double destruction, it is actually two different objects that are
destroyed.
I want it, in case, when the exact derived class is calculated after
some computation, inside constructor (Not in initializer list) and
assigned later.
To give an idea, say the code is a builder like,

class DerivedBuilder{
private:
smart_ptr<Base> pBase;
public:
DerivedBuilder(int type){
if(type < =0) {
pBase = smart_ptr<Base>(new Derived1()) ;
}
else if(type > 0 & <=10){
pBase = smart_ptr<Base>(new Derived3()) ;
}
else{
pBase = smart_ptr<Base>(new Derived2()) ;
}
}
};

Here it is synonymous to boost shared_ptr. I want pBase will call the
destructor only once.

That is because shared_ptr has a reference count and does not do deep-copy.


Best

Kai-Uwe Bux
 
R

Roland Pibinger

can anyone point to the problem.

Avoid 'smart pointers' and your 'smart pointer' related problems
disappear immediately.

Good luck,
Roland Pibinger
 
T

toton

Roland said:
Avoid 'smart pointers' and your 'smart pointer' related problems
disappear immediately.

Good luck,
If you have headache, will you cut your head!
How strange people can be!
 
M

mlimber

toton said:
If I write
auto_ptr<Base> pBase;
pBase = auto_ptr<Base>(new Derived(5));

I get the expected result. Derived destructor & Base destructor is
called only once.

Right because there's only one object and ownership is passed from one
auto_ptr to the other. In the case of shared_ptr with the same code,
there's still only one Base/Derived object in play, and the reference
count for that object could change (depending on your compiler's
optimization capabilities -- it might not exceed 1).
However If I use Axter smart_ptr (which is pretty common and has its
origin on Andrei Alexandrescu 's policy based smart pointers ),
smart_ptr<Base> pBase1;
pBase1 = smart_ptr<Base>(new Derived(5));
I get the destructor gets called twice. For a single line statement it
works fine.
can anyone point to the problem. The Base and Derived class are simple,
just to track emmory, has a cout in ctor and dtor.

See Kai-Uwe Bux's response elsethread.

Cheers! --M
 

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
473,755
Messages
2,569,536
Members
45,015
Latest member
AmbrosePal

Latest Threads

Top