我是 C++ 的新手,现在正在用它上课。作为家庭作业,我们应该编写一个接受任何容器作为输入但不使用迭代器的函数。所以我们不能只传递 std::begin(container)
和 std::end(container)
作为参数。我们必须将容器作为引用传递。我对此的看法是以下函数声明:
template <typename T, typename U, typename V, template <typename a, typename b> typename container>
void doStuff(container<T, U>& first, container<T, V>& second)
{
// the code
}
它接受两个容器(或任何使用两个模板参数的模板类型)。 container
中的第二个模板参数不同,因为在数组中 V
可能代表数组的大小,我希望能够接受两个不同大小的数组。
示例:
std::array<bool, 4> a1 = { true, false, false, false };
std::array<bool, 1> a2 = { false };
不幸的是,这个例子不起作用。该错误表明我 doStuff
不接受这些类型的参数。这是为什么?
在我看来,在这里使用“模板化模板”很重要,因为我想确保该函数只接受包含相同类型数据的两个容器。因此传递一个 int 数组和一个 double 数组应该是行不通的。
最佳答案
如果你想支持尽可能多的容器类型,你应该使用尽可能少的限制定义:
template <typename FirstContainer, typename SecondContainer>
void doStuff(FirstContainer& first, SecondContainer& second)
{
}
这是因为容器类型有各种各样的风格,例如std::array
是一个以值类型和静态大小作为参数的模板,std::vector
是一个以值类型和分配器为参数的模板,一些自定义 StringList
可能根本不是模板。
您的实现可能对支持的容器有一些特定要求,例如它可能只适用于整数类型的容器。但通常这只是实现的隐含结果。以一个简单的函数为例,将两个容器的值相加:
template <typename FirstContainer, typename SecondContainer>
int sum(const FirstContainer& first, const SecondContainer& second)
{
int result = 0;
for (auto value : first)
result += value;
for (auto value : second)
result += value;
return result;
}
此函数适用于可以添加到整数的任何值类型。如果无法添加(如 std::string
),最终将导致编译错误。
(请注意,可以使用自动推导的总和类型来编写更通用的函数,而不仅仅是 int
)
如果这些“隐式要求”对您来说还不够,您可以使用 static_assert
添加显式检查:
template <typename FirstContainer, typename SecondContainer>
int sum(const FirstContainer& first, const SecondContainer& second)
{
int result = 0;
for (auto value : first)
{
static_assert(std::is_same_v<int, decltype(value)>, "FirstContainer does not hold integers");
result += value;
}
for (auto value : second)
{
static_assert(std::is_same_v<int, decltype(value)>, "SecondContainer does not hold integers");
result += value;
}
return result;
}
现在您的函数只接受包含普通 int
的容器,没有其他内容。
您还可以使用 std::enable_if
为不受支持的容器完全“禁用”您的功能:
template <typename FirstContainer, typename SecondContainer>
auto sum(const FirstContainer& first, const SecondContainer& second)
-> std::enable_if_t<
std::is_same_v<typename FirstContainer::value_type, int> &&
std::is_same_v<typename SecondContainer::value_type, int>,
int
>
{
int result = 0;
for (auto value : first)
result += value;
for (auto value : second)
result += value;
return result;
}
现在您的函数仅限于具有嵌套 typedef value_type
以键入 int
的容器。
关于c++ - 如何在 C++ 中使用嵌套模板?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56915795/