4

这是字符串的构造:

string s {"Hello world!"};

并且字符串类具有以下我认为可能绑定到的构造函数:

从 char 指针/数组:

string (const char* s);

从初始化列表:

string (initializer_list<char> il);

起初我以为它会调用initializer_list,因为参数是支撑的。然后我看到 initializer_list 有一个参数,char但那是一个字符串。

然后我意识到{""}可以隐式转换为char[]因此它可能会调用第一个构造函数......在这种情况下,是否会在列表周围自动添加一对括号(例如({""}))?

那么它实际调用的是哪个构造函数呢?


这个怎么样:

double d1 (100);
double d2 {100};

他们是一样的吗?

假设字符串也有一个类似的构造函数string(initializer_list<string>),那么它会调用哪一个呢?

4

2 回答 2

8

在 C++11 中,花括号{}用于统一初始化。任何可以初始化的对象都可以用花括号进行初始化。优先考虑采用 的构造函数initializer_list<T>,因此如果花括号初始化可以匹配多个构造函数并且其中一个采用initializer_list,则将被选中。但是,如果没有initializer_list构造函数匹配,则还会考虑其他构造函数。

例如:

vector<int> two_elems{5,10}; // A vector containing two elements
vector<int> five_elems(5,10); // A vector containing five elements
vector<int> five_elems_also{10,10,10,10,10}; // Equivalent to the above

在您的示例中,您正在使用a 初始化stringa char const[13]initializer_list<char const*>如果有这样的构造函数,这将匹配,string但它不匹配initializer_list<char>。因此,参数改为与其他构造函数匹配,构造函数采用char const*是最佳匹配。

请注意,由于存在歧义,除非您打算使用构造函数,否则最好不要使用大括号初始化来初始化容器(例如vectorsetlist或什至 )。例如,无法调用使用大括号初始化的构造函数,因为该参数列表也将匹配构造函数。再举一个例子:stringinitializer_listvector<size_t>size_t, Tinitializer_list

vector<char const*> vec_of_strs{ 5, 0 }; // Creates a vector holding *5* nullptrs
vector<unsigned> vec_of_nums{ 5, 0 }; // Creates a vector holding *2* numbers

上面两行调用非常不同的构造函数并不是很明显,如果在维护期间将其中一个的类型更改为另一个(或代码出现在模板中),程序员可能会对突然的行为变化感到非常惊讶。

于 2013-08-02T21:45:39.063 回答
5
string(const char*)

语法{}不一定暗示.std::initializer_list

于 2013-08-02T21:14:22.040 回答