你应该使用模板模板参数:
template<typename T, template <typename, typename> class Container>
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
class MyMultibyteString
{
Container<T, std::allocator<T>> buffer;
// ...
};
这将允许您编写:
MyMultibyteString<int, std::vector> mbs;
这是一个正在编译的live example。编写上述内容的另一种方式可能是:
template<typename T,
template <typename, typename = std::allocator<T>> class Container>
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
class MyMultibyteString
{
Container<T> buffer; // <== No more need to specify the second argument here
// ...
};
这里是对应的live example。
你唯一需要注意的是模板模板参数声明中的参数数量和类型必须与你要作为模板传递的相应类模板的定义中的参数数量和类型完全匹配参数,而不管其中一些参数可能具有默认值。
例如,the class template std::vector accepts two template parameters(元素类型和分配器类型),尽管第二个具有默认值 std::allocator<T>。因此,你可以不写:
template<typename T, template <typename> class Container>
// ^^^^^^^^
// Notice: just one template parameter declared!
class MyMultibyteString
{
Container<T> buffer;
// ...
};
// ...
MyMultibyteString<int, std::vector> mbs; // ERROR!
// ^^^^^^^^^^^
// The std::vector class template accepts *two*
// template parameters (even though the second
// one has a default argument)
这意味着您将无法编写一个可以同时接受std::set 和std::vector 作为模板模板参数的类模板,因为与std::vector、the std::set class template accepts three template parameters 不同。