在c中,我可以用一个带有std :: string参数的构造函数编写一个类.由于隐式转换,这将允许我从std :: string或char *构造此类的实例.
是否有理由同时拥有std :: string构造函数和char *构造函数?
class MyStringClass {
public:
MyStringClass( const std::string &str ); // char *'s could implicitly use this constructor
MyStringClass( const char * str ); // would this ever be necessary?
};
这个问题也适用于函数参数.
void do_stuff_with_string( const std::string &str );
void do_stuff_with_string( const char * str );
编辑:
为了澄清,我想知道更多关于性能的信息.假设这些构造函数/函数正在调用只接受char *的api.如果我不需要,有两个单独的函数来避免构造一个std :: string是否值得?
void do_stuff_with_string( const std::string &str )
{
do_stuff_with_string( str.c_str() );
}
void do_stuff_with_string( const char * str )
{
// call some api that only accepts char *
}
最佳答案 如果您希望以不同方式处理C字符串和std ::字符串,则需要重载构造函数.
MyStringClass::MyStringClass( const std::string &str )
{
// Do std::string-specific stuff here.
}
MyStringClass::MyStringClass(const char * str )
{
// Do char* specific stuff here.
}
const char *的参数也可能不是以空字符结尾的C字符串,但实际上是指向单个字符或非空终止字符数组的指针.在这种情况下,隐式转换可能会失败.
例:
#include <iostream>
int DoStuff(const std::string &myString)
{
std::cout << myString << std::endl;
}
int main()
{
DoStuff("This is a null terminated c-string"); // Fine!
char charArray[] = { 'A', 'B', 'C' }; // Not null terminated!
DoStuff(charArray); // Uh oh!
}
上面的例子是一个函数,但同样也可以应用于构造函数.以上示例编译时没有警告!
在性能方面,由于std :: string(const char * const)构造函数将c-string复制到它自己的内部缓冲区中,因此肯定会受到打击.但是,在大多数情况下,影响可以忽略不计,因为副本非常有效.然而,对于非常大的字符串,它可能是一个问题.
但是,作为一般规则,尝试尽可能使用C字符串,并在需要C样式字符串时使用std :: string :: c_str()成员.在大多数情况下,偶尔从char *到std :: string的字符串副本将是一个微优化.只有在性能非常关键的代码中,这才是一个潜在的问题.