Aggregate initialization除其他外不需要用户提供的构造函数.但是std :: tuple和std :: pair对有一大组
overloaded constructors.从核心语言来看,这些构造函数是用户提供的还是用户声明的?
使用C 17可以编写(更新/澄清:其中nocopy是一个无法复制或移动的类,例如std :: mutex)
auto get_ensured_rvo_str(){ return std::pair(std::string(),nocopy()); }
编辑:不,这不可能在链接到答案和下面的答案中解释.
这需要聚合初始化(对于上下文:Multiple return values (structured bindings) with unmovable types and guaranteed RVO in C++17).
20.5.2.1 Construction
…
EXPLICIT constexpr tuple(const Types&…);6
Effects: The
constructor initializes each element with the value of the
corresponding parameter.
或者我们原则上可以编写自己的元组或对吗?
解决方法
不,在元组或对中没有支持将非移动类型传递给它们的构造函数,并且正如您所观察到的那样,因为构造函数参数和元组(或对)成员可以被观察为不同的对象:
// exposition only template<class... Us> tuple(Us&&... us) : values{std::forward<Us>(us)...} {} ^^ these ^^^^^^ are different objects to these
你必须使用分段构造:
return std::pair<std::string,nocopy>(std::piecewise_construct,std::forward_as_tuple(),std::forward_as_tuple());
Matt Calabrese在std-proposal列表上做了一个interesting point,现在我们已经保证了RVO应该可以编写接受工厂的组件来有效地构建他们的成员:
// hypothetical factory constructor return std::pair(std::factory_construct,[] { return std::string{}; },[] { return nocopy{}; });
另一个可能的方向是从元组和对中删除构造函数(或者更实际地,在没有构造函数的情况下编写类似于组件的组件)并依赖于new extensions to aggregate initialization应该允许通过多继承实现的元组和对的聚合初始化. Example.