为什么将nullptr返回为std :: string时不是编译时错误?

Tar*_*ron 24 c++ function stdstring language-lawyer

由于存在一个错误,我刚刚发现该代码可以在Visual Studio 17以及其他编译器上正常编译。现在我很好奇为什么?

#include <iostream>
#include <string>

std::string foo(){
    return nullptr;
}

int main(){
    auto s = foo();
    std::cout << s << std::endl;
}
Run Code Online (Sandbox Code Playgroud)

我可以想象这是因为std::basic_string可以用a调用c'tor char*,同时返回从ptr到的隐式转换std::string(使用NULLas作为参数,然后变为poof)。我走对了吗?

Som*_*ken 24

是的,您的假设是正确的,将检查std::basic_string构造函数#5

basic_string( const CharT* s,
              const Allocator& alloc = Allocator() );
Run Code Online (Sandbox Code Playgroud)

请注意,传递会nullptr调用标准和注释中所述的未定义行为:

如果[s, s + Traits::length(s))不是有效范围(例如,如果s是null指针,则行为未定义。


Evg*_*Evg 13

为什么不编译?std::string具有以下构造函数:

string(const CharT* s, const Allocator& alloc = Allocator());
Run Code Online (Sandbox Code Playgroud)

构造字符串,该字符串的内容使用指向的以空终止的字符串的副本进行初始化s。构造函数不是显式的,因此从nullptr到的隐式转换std::string确实是可能的。

  • @RichardCritten,绝对是。但是问题是为什么要编译该代码,而不是如果执行该代码会发生什么。UB不仅会发生在`nullptr`上,还会发生在任何不指向以null结尾的字符串开头的指针上。 (16认同)