【发布时间】:2019-10-24 14:03:55
【问题描述】:
是否有任何语法可以通过它在模板参数包的参数中分发非类型参数包,期望非类型包(不同大小)?由于这很令人困惑,我相信一个例子可能有助于澄清我的意思:https://godbolt.org/z/FaEGTV
template <typename T, int... I> struct Vec { };
struct A
{
template<template<typename, int...> typename... Container,
typename... Ts, int... Is>
A(Container<Ts,Is...>... );
};
A a(Vec<int, 0>{}, Vec<double, 0>{}); // ok
A b(Vec<int, 0, 1>{}, Vec<double, 0, 1>{}); // ok
A c(Vec<int, 0>{}, Vec<double, 0, 1>{}); // error
我希望标记为// error 的行使用类似于我所拥有的语法。显然,如果我编写一个特殊的构造函数来处理这种情况,它会正常工作。但是,我希望它适用于任意数量的容器,而无需针对所有可能的情况明确说明。例如,如果我有 2 个容器 a,b,索引集为 {0,1,2} 和 {0,1,2,3},则扩展应该类似于 A(a[0],a[1],a[2], b[0],b[1],b[2],b[3])。
我知道我可以递归地执行此操作,一次拆包一个容器,然后递归地委托给构造函数,期望在一开始只有一系列扁平元素。我的问题是,这是否以更优雅、更高效、更简洁的方式可行。
【问题讨论】:
-
嗯。在这个例子中,我什至对
b编译感到惊讶。 -
@Barry 因为通常不同大小的扩展不能一起工作?我认为是因为它仅限于
Container<Ts,Is...>。 -
Container<Ts,Is...>...说:对于Ts中的每个T,使用Container和T以及所有Is。这就是为什么所有Is必须相同的原因。编译示例的最简单方法是template <typename... Cs> A(Cs...);然后您可以使用帮助模板从Cs中的每个C中提取T和Is -
@IgorTandetnik 我知道
Is...在做什么。我希望我可以很好地扩展它。如前所述,我的另一个选择是使用递归,我现在正在尝试使用递归,但没有取得多大成功。 -
我认为伊戈尔的回答是最好的方式。根据您想要实现的确切目标,您根本不必使用递归。
标签: c++ templates c++17 variadic-templates index-sequence