Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/134.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/string/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++;可以为空的字符串 我习惯于在C++应用程序中传递这样的字符串: void foo(const std::string& input) { std::cout << input.size() << std::endl; } void bar() { foo("stackoverflow"); }_C++_String_Null - Fatal编程技术网

C++;可以为空的字符串 我习惯于在C++应用程序中传递这样的字符串: void foo(const std::string& input) { std::cout << input.size() << std::endl; } void bar() { foo("stackoverflow"); }

C++;可以为空的字符串 我习惯于在C++应用程序中传递这样的字符串: void foo(const std::string& input) { std::cout << input.size() << std::endl; } void bar() { foo("stackoverflow"); },c++,string,null,C++,String,Null,我可以将foo更改为: void foo(const std::string* input) { // TODO: support NULL input std::cout << input->size() << std::endl; } 我开始考虑从std::string继承并添加null属性,但我不太确定这是个好主意。对于可以为NULL的参数,最好只使用const char*字符串,但是如果我想保存字符串(或NULL)的副本而不必自己管理其内存,该怎么

我可以将
foo
更改为:

void foo(const std::string* input)
{
  // TODO: support NULL input
  std::cout << input->size() << std::endl;
}
我开始考虑从
std::string
继承并添加
null
属性,但我不太确定这是个好主意。对于可以为NULL的参数,最好只使用
const char*
字符串,但是如果我想保存字符串(或NULL)的副本而不必自己管理其内存,该怎么办?(见等)

有什么聪明的解决方案吗?

如果您只使用:

void foo(const char *xinput)
{
    if (xinput == NULL) {
        // do something exceptional with this
        return;
    }
    std::string input(xinput);
    // remainder of code as usual
}

是的,这确实会导致额外的分配和复制,调用该函数会更为冗长,因为在通常情况下需要使用
.c_str()
,但它确实提供了所需的语义。

我个人会将语义更改为传递空std::strings,而不是NULL:

void foo(const std::string& input)
{
    if (!input.empty())
        std::cout << input.size() << std::endl;
}

void bar()
{
      foo("");
}
void foo(const std::string和input)
{
如果(!input.empty())

std::cout如果希望类型为null,则将其设置为指针。传递字符串指针而不是引用,因为这正是指针可以做的,而引用不能。引用始终指向同一个有效对象。指针可以设置为null,也可以重置为指向另一个对象。因此,如果需要指针c要做的就是使用指针

或者,使用boost::optional,它允许使用更安全的方式指定“此变量可能包含值,也可能不包含值”


当然,也可以更改语义,这样您可以使用空字符串而不是null,传递一个单独的bool参数来指定字符串是否可用,或者重构,这样您就不需要这个了。

为什么不重载函数,并且不给第二个重载参数?然后两个重载都可以在内部调用一个函数,它提供读取逻辑,并向其自身传递一个指向
std::string
的指针

void foo_impl(string const* pstr) { … }

void foo(string const& str) {
    foo_impl(&str);
}

void foo() {
    foo_impl(0);
}

函数重载来拯救

void foo( const std::string& input )
{
    std::cout << input << std::endl;

    // do more things ...
}

void foo( const char* input )
{
    if ( input != NULL ) foo( std::string(input) );
}
void foo(const std::string和input)
{

std::cout或者,混合前面的两个答案:

void fooImpl( const char* input )
{
    if ( input != NULL )
        std::cout << input << std::endl;
}

void foo( const std::string& input )
{
    fooImpl(input.c_str());    
}

void foo( const char* input )
{
    fooImpl(input);
}
void fooImpl(常量字符*输入)
{
如果(输入!=NULL)

Std::CUT< P>绝对不继承从代码> STD::String 。继承是C++中最紧密的耦合,而只寻找可空性,可以简单地使用<代码> const char */COD>,重载,或者简单地<代码> STD::Stry*<代码>如果您真的想要。

为什么要NULL?IS?足够了?@Tim:也许吧。这样我就不用老是检查那些参数是否为NULL,我会用empty()检查“无值”。重新引入NULL是假的。如果你需要可怕的NULL指针,为什么首先要使用引用?实际上,使用引用最重要的原因之一是你可以确保它不是NULL。我不会这么做,这可能会误导。这是重点,真的;这是一个抽象。使用应该很简单,除非你非常关心性能。@sudarkoff:我不同意。问题本身具有误导性,需要抽象。解决方案非常优雅。至于性能问题,“过早优化,等等。”…+1.两点:首先,空字符串可以是有效值,与null分开。其次,当您只关心大小是否为非零时,使用
empty()
而不是
size()
被认为是更好的解决方案。
boost::optional
或指针。改为使用empty()。对原始问题的评论指出,使用NULL表示“不知道值”,使用empty表示“空值”。这使得这个答案是错误的。但我想再看一看,因为传递指针会带来“谁拥有这个指针?”问题。在这种情况下,boost::optional或智能指针将是最佳选择。
void foo( const std::string& input )
{
    std::cout << input << std::endl;

    // do more things ...
}

void foo( const char* input )
{
    if ( input != NULL ) foo( std::string(input) );
}
void fooImpl( const char* input )
{
    if ( input != NULL )
        std::cout << input << std::endl;
}

void foo( const std::string& input )
{
    fooImpl(input.c_str());    
}

void foo( const char* input )
{
    fooImpl(input);
}