[英]No viable conversion from 'const std::__1::basic_string<char> to 'std::__1::basic_string<char> *'
[英]Private inheritance from std::basic_string
我一直在尝试了解有关私有继承的更多信息,并决定创建一个从std::basic_string
继承的string_t
类。 我知道很多人都会告诉我从STL类继承是一个坏主意,如果我想扩展其功能,最好创建全局函数以接受对这些类实例的引用。 我同意,但是就像我之前说的,我正在尝试学习如何实现私有继承。
到目前为止,这是该类的样子:
class string_t :
#if defined(UNICODE) || defined(_UNICODE)
private std::basic_string<wchar_t>
#else
private std::basic_string<char>
#endif
{
public:
string_t() : basic_string<value_type>() {}
string_t( const basic_string<value_type>& str )
: basic_string<value_type>( str ) {}
virtual ~string_t() {}
using std::basic_string<value_type>::operator=; /* Line causing error */
std::vector<string_t> split( const string_t& delims )
{
std::vector<string_t> tokens;
tokens.push_back( substr( 0, npos ) );
}
};
我收到以下错误:
1>c:\program files\microsoft visual studio 9.0\vc\include\xutility(3133) : error C2243: 'type cast' : conversion from 'const string_t *' to 'const std::basic_string &' exists, but is inaccessible 1> with 1> [ 1> _Elem=wchar_t, 1> _Traits=std::char_traits, 1> _Ax=std::allocator 1> ] 1> c:\program files\microsoft visual studio 9.0\vc\include\xutility(3161) : see reference to function template instantiation 'void std::_Fill(_FwdIt,_FwdIt,const _Ty &)' being compiled 1> with 1> [ 1> _Ty=string_t, 1> _FwdIt=string_t * 1> ] 1> c:\program files\microsoft visual studio 9.0\vc\include\vector(1229) : see reference to function template instantiation 'void std::fill(_FwdIt,_FwdIt,const _Ty &)' being compiled 1> with 1> [ 1> _Ty=string_t, 1> _FwdIt=string_t * 1> ] 1> c:\program files\microsoft visual studio 9.0\vc\include\vector(1158) : while compiling class template member function 'void std::vector::_Insert_n(std::_Vector_const_iterator,unsigned int,const _Ty &)' 1> with 1> [ 1> _Ty=string_t, 1> _Alloc=std::allocator 1> ] 1> c:\work\c++\string_t\string_t.h(658) : see reference to class template instantiation 'std::vector' being compiled 1> with 1> [ 1> _Ty=string_t 1> ]
最后一个错误中的行号(658)指向split()
函数定义的左括号。 如果我注释掉using std::basic_string<value_type>::operator=;
的错误,我可以摆脱using std::basic_string<value_type>::operator=;
线。 据我了解, using
关键字指定将赋值运算符在string_t
内从private
范围string_t
到public
范围。
为什么会出现此错误,我该如何解决?
另外,我的string_t
类不包含它自己的单个数据成员,更不用说动态分配的成员了。 因此,如果我不为此类创建析构函数,那是否意味着如果有人要使用基类指针delete
string_t
实例, string_t
调用基类析构函数?
当我为string_t
定义了析构函数时,以下代码引发异常,但是当我用VS2008编译时将析构函数注释掉时,以下代码将起作用。
basic_string<wchar_t> *p = new string_t( L"Test" );
delete p;
您的默认构造函数不应是显式的。 我认为明确可能是它也无法将std::string
转换为string_t
的原因,但是您从代码段:vP中删除了该string_t
。
该程序可以在GCC 4.2上编译并正常运行:
#include <iostream>
#include <string>
#include <vector>
using namespace std;
class string_t :
#if defined(UNICODE) || defined(_UNICODE)
private std::basic_string<wchar_t>
#else
private std::basic_string<char>
#endif
{
public:
string_t() : basic_string<value_type>() {}
string_t( const basic_string<value_type>& str )
: basic_string<value_type>( str ) {}
virtual ~string_t() {}
using std::basic_string<value_type>::operator=; /* Line causing error */
std::vector<string_t> split( const string_t& delims )
{
std::vector<string_t> tokens;
for ( size_t pen = 0, next = 0; next != npos; pen = next + 1 ) {
next = find_first_of( delims, pen );
if ( pen != next ) tokens.push_back( substr( pen, next - pen ) );
}
return tokens;
}
template<class os>
friend os &operator<<(os &, string_t const&);
};
template< class os_t >
os_t &operator<<( os_t &os, string_t const &str ) {
return os << static_cast< string >(str);
}
int main( int argc, char ** argv ) {
vector<string_t> mytoks = string_t( argv[1] ).split( string( "_" ) );
for ( vector<string_t>::iterator it = mytoks.begin(); it != mytoks.end(); ++ it ) {
cerr << * it << endl;
}
return 0;
}
您需要提供合适的转换构造函数:
string_t(const std::basic_string<value_type>&);
否则,编译器不知道如何构建一个string_t
从std::basic_string<>
当你添加元素的矢量string_t
秒。
关于更新:
如果operator=()
是私有的,则using
声明无济于事。 为什么不只是实现自己的operator=()
而是转发分配:
string_t& operator=(const string_t& s)
{
basic_string<value_type>::operator=(s);
return *this;
}
有了它对我来说很好。
不幸的是,您已经遗漏了足够多的信息,无法确定如何得到已记录的错误消息(并且编译时我们不知道657行是什么也无济于事)。
当前可能似乎是substr()
返回一个std :: string,并且编译器不确定如何将其转换为string_t
(这就是您要它存储在向量中的内容)。 您可能需要/想要添加一个ctor来处理此问题,例如:
string_t(std::string const &init) : std::string(init) {}
这样一来,编译器便知道如何将substr()
返回的substr()
转换为string_t
,它可以根据您的请求将其推入向量中。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.