Click here to Skip to main content
15,886,873 members
Please Sign up or sign in to vote.
4.00/5 (1 vote)
See more:
Hello all,

I'm in process converting some of our 3rd party source modules (written/build with VC++ 6.0) to make them build within VS2008/2010 too. With the newer compilers also some C++ rules have been made more strictly.
Unfortunately I'm now running into conversion issue related to an own class template based around the auto_ptr class template. And to be more exactly: the copy constructor.
The headerfile of the own implemented auto_ptr template:

#ifndef __MY_AUTO_PTR_H
#define __MY_AUTO_PTR_H
#include <vector>
template <class T>
class my_auto_ptr : public std::auto_ptr<T>
{
public:
    my_auto_ptr() : std::auto_ptr<T>(){}
    my_auto_ptr(T* p):std::auto_ptr<T>(p){}
my_auto_ptr(const my_auto_ptr & lp)   :std::auto_ptr<T>(lp){ }
    bool operator < (const std::auto_ptr<T> &pt) const { return *get() < *pt ;}
    bool operator == (const std::auto_ptr<T> &pt) const { return *get() == *pt ;}
};
#endif

The C++ compiler fails over the 'my_auto_ptr(const...' above the bool operator.
The compiler throws next error message to me:

XML
c:\...\my_auto_ptr.h(19) : error C2664: 'std::auto_ptr<_Ty>::auto_ptr<T>(std::auto_ptr<_Ty> &) throw()' : cannot convert parameter 1 from 'const my_auto_ptr<T>' to 'std::auto_ptr<_Ty> &'
        with
        [
            _Ty=CLine,
            T=CLine
        ]
        and
        [
            T=CLine
        ]
        and
        [
            _Ty=CLine
        ]
        Conversion loses qualifiers
        c:\...\my_auto_ptr.h(19) : while compiling class template member function 'my_auto_ptr<T>::my_auto_ptr(const my_auto_ptr<T> &)'
        with
        [
            T=CLine
        ]
        C:\Program Files\Microsoft Visual Studio 9.0\VC\atlmfc\include\afxtempl.h(1257) : see reference to class template instantiation 'my_auto_ptr<T>' being compiled
        with
        [
            T=CLine
        ]
Etc...



I'm afraid that I'm a bit lost here by now...

Do you guys have a suggestion?
Thx in advance,
EiSl
Posted

The problem is that std::auto_ptr does not have a "standard copy constructor".

The prototype for auto_ptr copy is
auto_ptr(auto_ptr&)

(note the non const parameter).

You are passing a const to something that is designed to modify it.

The proper way to do this is having a
C++
//non-const reference
my_autoptr(myautoptr& s) :auto_ptr(s) {}

//pure value (relies of auto_ptr::operator ref() )
my_autoptr(typename auto_ptr::ref s) :auto_ptr(s) {} 


Note: auto_ptr doesn't have virtual methods, so don't use auto_ptr and my_autoptr polymorphicaly.
 
Share this answer
 
Comments
eslange 7-Apr-11 4:41am    
Thanks for your suggestion - I really appreciate it!


The const was indeed a logical one after all.

Unfortunately...
The auto_ptr::ref is rejected by VS2008 with next error:
[pre]
error C2039: 'ref' : is not a member of 'std::auto_ptr<_Ty>'
[/pre]
Also the copy constructor is not completely covered now...
When removing the const, I run into next compiler issue:
[pre]
C:\Program Files\Microsoft Visual Studio 9.0\VC\include\vector(1211) : error C2558: class 'my_auto_ptr<t>' : no copy constructor available or copy constructor is declared 'explicit'

with [ T=CLine ]

C:\Program Files\Microsoft Visual Studio 9.0\VC\include\vector(1153) : while compiling class template member function 'void std::vector<_Ty>::_Insert_n(std::_Vector_const_iterator<_Ty,_Alloc>,unsigned int,const _Ty &)'

with [ _Ty=LINEPTR,

_Alloc=std::allocator<LINEPTR> ]

c:\.....\Provider.h(116) : see reference to class template instantiation 'std::vector<_Ty>' being compiled

with [ _Ty=LINEPTR ]

C:\Program Files\Microsoft Visual Studio 9.0\VC\include\vector(1235) : error C2558: class 'my_auto_ptr<t>' : no copy constructor available or copy constructor is declared 'explicit'

with [ T=CLine ]
[/pre]
Where the LINEPTR is defined: typedef my_auto_ptr<cline> LINEPTR;
Emilio Garavaglia 7-Apr-11 6:28am    
Sorry, many STL implementation don't declare a ref struct into auto_ptr, but a separate auto_ptr_ref.
See http://www.cplusplus.com/reference/std/memory/
Nicolai Josuttis in his book "The C++ Standard Library" (section 4.2 on Class auto_ptr) says "According to the concept of auto_ptrs, it is possible to transfer ownership into a function by using a constant reference. This is very dangerous because people usually expect that an object won't get modified when you pass it as a constant reference. Fortunately, there was a late design decision that made auto_ptrs less dangerous. By some tricky implementation techniques, transfer of ownership is not possible with constant references. In fact you can't change the ownership of an constant auto_ptr..."

If I understand this discussion in Josuttis correctly, it appears that you may have run into an improvement of the compiler, making it more strict and also making your source requiring a change.

The Josuttis book seems to be a pretty good reference on the STL and the general consensus is that it belongs on every C++ programmer's bookshelf.
 
Share this answer
 

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900