正如您已经被暗示的那样,最好的方法是使用元组:
template<typename ...AcceptedTypes> // e.g. MyClass<T1, T2>
class MyClass {
std::tuple<std::vector<AcceptedTypes>...> vectors;
};
这是乘以“字段”的唯一方法,因为您无法神奇地拼出字段名称。另一件重要的事情可能是对它们进行命名访问。我想您想要实现的是拥有多个具有 unique 类型的向量,因此您可以使用以下工具通过其值类型“搜索”正确的向量:
template <class T1, class T2>
struct SameType
{
static const bool value = false;
};
template<class T>
struct SameType<T, T>
{
static const bool value = true;
};
template <typename... Types>
class MyClass
{
public:
typedef std::tuple<vector<Types>...> vtype;
vtype vectors;
template<int N, typename T>
struct VectorOfType: SameType<T,
typename std::tuple_element<N, vtype>::type::value_type>
{ };
template <int N, class T, class Tuple,
bool Match = false> // this =false is only for clarity
struct MatchingField
{
static vector<T>& get(Tuple& tp)
{
// The "non-matching" version
return MatchingField<N+1, T, Tuple,
VectorOfType<N+1, T>::value>::get(tp);
}
};
template <int N, class T, class Tuple>
struct MatchingField<N, T, Tuple, true>
{
static vector<T>& get(Tuple& tp)
{
return std::get<N>(tp);
}
};
template <typename T>
vector<T>& access()
{
return MatchingField<0, T, vtype,
VectorOfType<0, T>::value>::get(vectors);
}
};
这是测试用例,您可以尝试一下:
int main( int argc, char** argv )
{
int twelf = 12.5;
typedef reference_wrapper<int> rint;
MyClass<float, rint> mc;
vector<rint>& i = mc.access<rint>();
i.push_back(twelf);
mc.access<float>().push_back(10.5);
cout << "Test:\n";
cout << "floats: " << mc.access<float>()[0] << endl;
cout << "ints: " << mc.access<rint>()[0] << endl;
//mc.access<double>();
return 0;
}
如果您使用的任何类型不在您传递给专门化 MyClass 的类型列表中(请参阅this commented-out access for double),您将收到编译错误,不太可读,但 gcc 至少指出导致问题的正确位置,并且至少这样的错误消息表明问题的正确原因 - 例如,如果您尝试执行 mc.access(): p>
error: ‘value’ is not a member of ‘MyClass<float, int>::VectorOfType<2, double>’