给出以下代码:
struct B { };
struct A
{
A(const B&);
};
void g()
{
B a;
const A& b = a;
}
[dcl.init.ref]中似乎没有合适的措辞可以使此形式井井有条(具体而言,没有措辞说明只有用户定义的转换是通过转换构造函数构造临时对象时会发生什么情况)
first case不适用([over.match.ref]不考虑构造函数),second case(同样,[over.match.ref]不考虑构造函数)也不适用,这给我们留下了third case,因为其中一种类型是类类型,并且A
与B
无关。第三种情况是:
如果
T1
或T2
是类类型并且T1
与T2
没有引用关系,则使用复制初始化规则考虑用户定义的转换通过用户定义的转换来转换类型为“cv1 T1
”的对象;如果相应的非引用副本初始化格式不正确,则程序格式不正确。 调用转换函数的结果(如非引用复制初始化所述)将用于直接初始化引用。对于这种直接初始化,用户定义的转换不是考虑过的。
乍看之下还不错,但它仅定义了何时选择转换函数进行转换的情况,而没有说明何时选择转换构造函数(此处适用[over.match.copy]的规则) )。如果选择了这样的构造函数,则必须由该构造函数创建并初始化一个临时对象,然后将其绑定到该引用,但是适用子句中没有提及此对象。是否缺少措辞,还是我缺少什么?
答案 0 :(得分:2)
我想念东西吗?
据我所知。
措辞
[dcl.init.ref]
...使用用户定义的转换来复制类型为“ cv1 T1”的对象的对象进行初始化的规则将被视为用户定义的转换,否则显然会允许构造([dcl.init],[over.match .copy],[over.match.conv])...
其本身显然允许(或将允许)使用converting构造函数进行转换。它甚至指的是[over.match.copy]
[over.match.copy]
...候选功能的选择如下:
T的转换构造函数([class.conv.ctor])是候选函数。
...
第一个引号的有问题的延续:
...调用转换函数的结果...
没有明确声明未考虑转换构造函数,而是似乎假定“转换函数”涵盖了此上下文中所有可能的用户定义的转换。
因此,我怀疑不打算不考虑转换构造函数,而是认为规则的措辞是一种疏忽。可能源于这样的事实,即转换构造函数也是执行转换的函数,因此“转换函数”一词描述了它们,即使这是其他类型的用户定义转换的确切名称。
如果我的猜想是正确的,则该规则可能应该重新措词。