T
tsar.omen
Hello everyone,
during my coding practice I have encounted the following problem:
Vital code pieces:
---
template <class T> class SmartPtr
{
private:
Reference<T>* ref; // object with pointer to T and ref counter
public:
SmartPtr() : ref(0) {}
SmartPtr(T* t) : ref(new Reference<T>(t)) {}
SmartPtr(SmartPtr& h) : ref(h.acquire()) {}
SmartPtr& operator = (T* t) {/**/}
SmartPtr& operator = (SmartPtr& h) {/**/}
~SmartPtr() { freeReference(); }
private:
void freeReference() {/**/}
Reference<T>* acquire () {/**/}
};
---
Now to introduce the problem:
(1) works:
SmartPtr<Foo> pFoo(new Foo()); // direct initialization
(SmartPtr::SmartPtr(T*))
(2) works:
SmartPtr<Foo> pFoo1(new Foo());
SmartPtr<Foo> pFoo2(pFoo1); // direct initialization
(SmartPtr::SmartPtr(SmartPtr&))
(3) works:
SmartPtr<Foo> pFoo; // SmartPtr::SmartPtr()
pFoo = new Foo(); // operator=(T *)
pFoo = pFoo7; // operator=(SmartPtr&)
!(4) does _NOT_ work:
SmartPtr<Foo> pFoo = new Foo();
It produces the following error on gcc 3.3.6:
---
main.cc:24: error: no matching function for call to
`SmartPtr<Point>::SmartPtr( SmartPtr<Point>)'
smartptr.h:162: error: candidates are:
SmartPtr<T>::SmartPtr(SmartPtr_ref<T>)
[with T = Point]
smartptr.h:73: error:
SmartPtr<T>::SmartPtr(SmartPtr<T>&) [with T = Point]
smartptr.h:70: error: SmartPtr<T>::SmartPtr(T*) [with T
=
Point]
main.cc:24: error: initializing temporary from result of `
SmartPtr<T>::SmartPtr(T*) [with T = Point]'
---
AFAIK in case 'SmartPtr<Foo> pFoo = new Foo();' a copy initialization
is used. That's firstly applying conversion operator to the right side
and then calling a copy constructor. Because right side in in fast T* t
so SmartPtr::SmartPtr(T*) was chosen, resulting in creation of
temporary object and trying to copy initialize pFoo with tmp object
which fails [SmartPtr<Point>::SmartPtr(SmartPtr<Point>) as reported by
g++].
My question is if it's possible to somehow fix it to allow construction
like 'SmartPtr<Foo> pFoo = new Foo();' legal.
Many thanks in advance.
during my coding practice I have encounted the following problem:
Vital code pieces:
---
template <class T> class SmartPtr
{
private:
Reference<T>* ref; // object with pointer to T and ref counter
public:
SmartPtr() : ref(0) {}
SmartPtr(T* t) : ref(new Reference<T>(t)) {}
SmartPtr(SmartPtr& h) : ref(h.acquire()) {}
SmartPtr& operator = (T* t) {/**/}
SmartPtr& operator = (SmartPtr& h) {/**/}
~SmartPtr() { freeReference(); }
private:
void freeReference() {/**/}
Reference<T>* acquire () {/**/}
};
---
Now to introduce the problem:
(1) works:
SmartPtr<Foo> pFoo(new Foo()); // direct initialization
(SmartPtr::SmartPtr(T*))
(2) works:
SmartPtr<Foo> pFoo1(new Foo());
SmartPtr<Foo> pFoo2(pFoo1); // direct initialization
(SmartPtr::SmartPtr(SmartPtr&))
(3) works:
SmartPtr<Foo> pFoo; // SmartPtr::SmartPtr()
pFoo = new Foo(); // operator=(T *)
pFoo = pFoo7; // operator=(SmartPtr&)
!(4) does _NOT_ work:
SmartPtr<Foo> pFoo = new Foo();
It produces the following error on gcc 3.3.6:
---
main.cc:24: error: no matching function for call to
`SmartPtr<Point>::SmartPtr( SmartPtr<Point>)'
smartptr.h:162: error: candidates are:
SmartPtr<T>::SmartPtr(SmartPtr_ref<T>)
[with T = Point]
smartptr.h:73: error:
SmartPtr<T>::SmartPtr(SmartPtr<T>&) [with T = Point]
smartptr.h:70: error: SmartPtr<T>::SmartPtr(T*) [with T
=
Point]
main.cc:24: error: initializing temporary from result of `
SmartPtr<T>::SmartPtr(T*) [with T = Point]'
---
AFAIK in case 'SmartPtr<Foo> pFoo = new Foo();' a copy initialization
is used. That's firstly applying conversion operator to the right side
and then calling a copy constructor. Because right side in in fast T* t
so SmartPtr::SmartPtr(T*) was chosen, resulting in creation of
temporary object and trying to copy initialize pFoo with tmp object
which fails [SmartPtr<Point>::SmartPtr(SmartPtr<Point>) as reported by
g++].
My question is if it's possible to somehow fix it to allow construction
like 'SmartPtr<Foo> pFoo = new Foo();' legal.
Many thanks in advance.