struct X {
X() {}
X(X&&) { }
};
X global_m;
struct Converts {
operator X&& () const { return std::move(global_m); }
};
我相信以下内容应该有效:
X x { Converts{} };
X只有一个单参数构造函数。它需要一个X&&
。 Converts对象是临时的,它将转换为X&&
。那么为什么我会从clang-3.3中得到这个错误信息:
// error: "candidate constructor not viable: no known conversion from 'Converts' to 'X &&' for 1st argument"
我能够明确地将运营商称为:
X x { Converts{}.operator struct X&& () }; // this works.
对我来说不幸的是,它适用于ideone,据我所知,它基于g ++。是否有任何在线clang编译器现在正在运行?
答案 0 :(得分:1)
根据这个answer,这是标准中的缺陷。这是对提议的标准@ecatmur的修正。
4 - 但是,在考虑构造函数或用户定义的转换函数的参数时,它是一个候选者:
- by 13.3.1.3 [over.match.ctor]在类复制初始化的第二步中复制临时时调用,或者
- 由13.3.1.4 [over.match.copy],13.3.1.5 [over.match.conv]或13.3.1.6 [over.match.ref]在所有情况下,
仅考虑标准转换序列和省略号转换序列;当将初始化列表作为单个参数传递或初始化列表只有一个元素时,在考虑13.3.1.7 [over.match.list]的候选类
X
的构造函数的第一个参数时,用户定义的转换为X
或引用(可能 cv -qualified)X
仅在转换函数指定其用户定义的转换时才被考虑。 [注意:因为在列表初始化的上下文中隐式转换序列中允许多个用户定义的转换,所以这个限制对于确保X
的转换构造函数是必需的,使用不是a
类型的单个参数X
或从X
派生的类型调用,对于使用临时{{1}调用的X
的构造函数不明确对象本身是从X
构造的。 - 结束记录]
我不知道这是不是标准最终如何被更改(因为我只有一个草稿)但是我会假设某些事情已经完成,因为结果的变化取决于编译器版本