#include <iostream>
#include <string>
#include <initializer_list>
class A
{
public:
A(int, bool) { std::cout << __PRETTY_FUNCTION__ << std::endl; }
A(int, double) { std::cout << __PRETTY_FUNCTION__ << std::endl; }
A(std::initializer_list<int>) { std::cout << __PRETTY_FUNCTION__ << std::endl; }
};
int main()
{
A a1 = {1, 1.0};
return 0;
}
(这个问题是对此的后续。)
上面的程序无法编译clang35 -std=c++11
init.cpp:15:14: error: type 'double' cannot be narrowed to 'int' in initializer list [-Wc++11-narrowing]
A a1 = {1, 1.0};
^~~
init.cpp:15:14: note: insert an explicit cast to silence this issue
A a1 = {1, 1.0};
^~~
static_cast<int>( )
whileg++48 -std=c++11
选择一个产生警告来诊断畸形变窄
init.cpp: In function ‘int main()’:
init.cpp:15:17: warning: narrowing conversion of ‘1.0e+0’ from ‘double’ to ‘int’ inside { } [-Wnarrowing]
A a1 = {1, 1.0};
^
init.cpp:15:17: warning: narrowing conversion of ‘1.0e+0’ from ‘double’ to ‘int’ inside { } [-Wnarrowing]
并产生结果
A::A(std::initializer_list<int>)
我的问题是是否A::A(std::initializer_list<int>)
应该是一个可行的超载。以下是我认为暗示initializer_list
过载不可行的标准报价。
从13.3.2 [over.match.viable]
其次,为了
F
成为一个可行的函数,每个参数都应该存在一个隐式转换序列,该序列将该参数转换为 的相应参数F
。
从4 [conv]
当且仅当声明;时,表达式
e
才能隐式转换为类型 对于某些发明的临时变量,格式正确。T
T t=e
t
从8.5.1 [dcl.init.aggr]
如果初始化子句是一个表达式并且需要一个窄化转换来转换该表达式,那么程序是非良构的。
使用8.5.1
and 4
,因为下面的格式不正确
std::initializer_list<int> e = {1, 1.0};
{1, 1.0}
不能隐式转换为std::initializer_list<int>
.
使用来自 的引用,难道13.3.2
不应该暗示A::A(std::initializer_list<int>)
在为 A a1 = {1, 1.0};
找不到可行initializer_list
的构造函数,这句话不应该选择A::A(int, double)
吗?