我有一个这样定义的变量
auto drum = std::make_tuple
( std::make_tuple
( 0.3f
, ExampleClass
, [](ExampleClass& instance) {return instance.eGetter ();}
)
);
我希望drum
是一个元组。 (即((a, b, c))
)。
我还有另一个这样定义的变量
auto base = std::make_tuple
( 0.48f
, ExampleClass
, [](ExampleClass& instance) {return instance.eGetter ();}
);
我希望这只是三个元素(即(a, b, c)
)的元组
我还有一个向量定义如下
std::vector<std::tuple<std::tuple< float
, ExampleClass
, std::function<float (ExampleClass&)>
>>> listOfInstruments;
现在,如果我将drum
添加到listOfInstruments
,我希望不会出错。
listOfInstruments.push_back(drum);
确实是这种情况
listOfInstuments.push_back(base);
是我期望出现错误的地方,但是代码可以很好地编译。
由于listOfInstruments
的类型为'tuple of tuples',难道不应该仅添加'tuple'引起一些错误?除非()
将(())
和std::vector
视为相同类型。还是我完全错了,这里还有其他工作吗?
似乎无法弄清楚。
答案 0 :(得分:32)
在这里,线索和向量大多是红色鲱鱼。有效的方式很简单,就是push_back
像任何函数一样,可以对其参数执行隐式转换,如以下工作片段所示:
#include <vector>
struct A { };
struct B {
B(A const &) { }
};
int main() {
std::vector<B> v;
v.push_back(A{});
}
回到元组,我们可以看到它(除其他外)有一个条件明确的构造函数(#2 here),该构造函数引用了要成为元组的成员的条件:
tuple( const Types&... args );
当且仅当所有成员都具有隐式副本构造器时,此构造器才是隐式的(在这种情况下(因为综合构造器确实是隐式的))。这意味着std::tuple<...>
可隐式转换为std::tuple<std::tuple<...>>
,这就是您要观察的内容。