正在调用错误的构造函数

时间:2017-01-14 19:06:08

标签: c++ c++11 constructor

我有一个创建不同类型变量的类。

通过一些宏定义,我们想要初始化这些变量。

#define NUMBER(number)      JsonVariable(number)
#define STRING(text)        JsonVariable(text)
#define TRUE                JsonVariable(true)
#define FALSE               JsonVariable(false)

数字初始化正常,但是Strings会因为未知原因调用Bool构造函数。

JsonVariable(string x)
    : type(String), s(x)
{
    cout << "String" << x << endl;
    sleep
}
JsonVariable(bool x)
    : type(Boolean), b(x)
{
    cout << "Boolean" << x << endl;
    sleep
}

如果我注释掉Bool构造函数,则调用String one。

有什么建议吗?

修改 这是一个带有已定义宏的字符串构造函数。 std :: string用在构造函数中。

JSON(test) = STRING("Hello")

Type是定义的枚举。此外,还必须使用宏作为此分配的一部分。

EDIT2:澄清。这是枚举类型。

std :: string与命名空间std一起使用,因而是单个字符串。 String也来自枚举类型

String != string

typedef enum {
    Null, Integer, Double, Boolean, String, Object, Array
} datatype;

2 个答案:

答案 0 :(得分:3)

您可能会遇到转化规则的影响。如果您传递const char*,则bool超载优先于std::string&

void f(std::string&) { std::cout << "string"; }
void f(bool) { std::cout << "bool"; }

int main() {
    f("abc"); // prints 'bool'
}

这是合乎逻辑的:通常会检查指针是否为非零,因此需要转换为int / bool类型。另一方面,绑定到const std::string&意味着std::string构造函数参考。由于temporaries不绑定到非const引用,因此绑定到std::string&是不可能的。

解决方法是手动创建字符串,或者最好是拥有const char*的构造函数。

答案 1 :(得分:2)

根据经验,只要您的API公开此签名的重载函数或构造函数(或其CV限定和/或引用变体):

void func(std::string){}
void func(bool){}

您应始终为const char*

提供一个
void func(std::string){}
void func(bool){}
void func(const char* c){ func(std::string(c)); }

否则您和您的用户(特别是)可能因为:

而出现微妙的惊喜

string-literals (例如"abc...")迅速衰减到const char*,通过重载解析,转换为bool的优先级高于用户定义的转换std::string所做的。