字符串文字匹配bool重载而不是std :: string

ser*_*0ne 35 c++ string boolean overloading overload-resolution

我正在尝试编写一个包含一些重载方法的C++类:

class Output
{
public:
    static void Print(bool value)
    {
        std::cout << value ? "True" : "False";
    }

    static void Print(std::string value)
    {
        std::cout << value;
    }
};
Run Code Online (Sandbox Code Playgroud)

现在让我说我调用方法如下:

Output::Print("Hello World");
Run Code Online (Sandbox Code Playgroud)

结果就是这样

真正

那么,为什么,当我定义该方法可以接受布尔值和字符串时,当我传入一个非布尔值时,它是否使用布尔重载?

编辑:我来自C#/ Java环境,对C++来说还是新手!

Jos*_*eld 44

"Hello World"是一个"12的数组const char" 类型的字符串文字,可以转换为"指针const char",然后可以转换为a bool.这正是发生的事情.编译器更喜欢使用std::string转换构造函数.

涉及转换构造函数的转换序列称为用户定义的转换序列.从"Hello World"a到a 的转换bool标准转换序列.该标准规定标准转换序列总是优于用户定义的转换序列(第13.3.3.2/2节):

标准转换序列(13.3.3.1.1)是比用户定义的转换序列或省略号转换序列更好的转换序列

这个"更好的转换序列"分析是针对每个可行函数的每个参数进行的(并且您只有一个参数),并且通过重载决策选择更好的函数.

如果你想确保std::string调用版本,你需要给它一个std::string:

Output::Print(std::string("Hello World"));
Run Code Online (Sandbox Code Playgroud)

  • 如果有人调用`Output :: Print(“ Hello World”),将其转换为不是的Output :: Print(bool value),则如何强制错误或“正确的”(按预期的含义)转换有人期望什么? (2认同)

Zac*_*ann 12

不知道为什么没有人发布这个,但您可以添加另一个重载,为您从 const char* 转换为 std::string。这使调用者不必担心这一点。

class Output
{
public:
    static void Print(bool value)
    {
        std::cout << value ? "True" : "False";
    }

    static void Print(std::string value)
    {
        std::cout << value;
    }

    // Just add the override that cast to std::string
    static void Print(const char* value)
    {
        Output::Print(std::string(value));
    }
};
Run Code Online (Sandbox Code Playgroud)


aki*_*kim 5

FWIW,如果您不想为添加重载,可以通过这种方式解决(如果可以使用模板)const char*

#include <iostream>
#include <string>
#include <type_traits>

template <typename Bool,
          typename T = std::enable_if_t<std::is_same<Bool, bool>{}>>
void foo(Bool)
{
  std::cerr << "bool\n";
}

void foo(const std::string&)
{
  std::cerr << "string\n";  
}

int main()
{
  foo("bar");
  foo(false);
}
Run Code Online (Sandbox Code Playgroud)