【发布时间】:2014-12-21 12:57:08
【问题描述】:
假设我们有以下类型
template <bool... Values>
struct foo{};
我想从 constexpr 数组 bool tab[N] 创建一个可变参数模板。换句话说,我想做这样的事情:
constexpr bool tab[3] = {true,false,true};
using ty1 = foo<tab[0], tab[1], tab[2]>;
但我想以编程方式进行。目前,我尝试了以下方法:
template <std::size_t N, std::size_t... I>
auto
mk_foo_ty(const bool (&tab)[N], std::index_sequence<I...>)
{
// error: template argument for template type parameter must be a type
return foo<tab[I]...>{};
}
// error (see mk_foo_ty)
using ty2 = decltype(mk_ty(tab, std::make_index_sequence<3>{}));
// error: expected '(' for function-style cast or type construction
using ty3 = foo<(tab[std::make_index_sequence<3>])...>;
我什至不确定这是否可能。也许诉诸 Boost.Preprocessor 之类的东西,但我不喜欢这个主意。那么,有人有想法吗?谢谢!
编辑
一方面我有一个constexpr 布尔方阵的框架,可以在编译时使用异或、否定等创建。
另一方面,我有一个模板框架,它使用以布尔值作为参数的可变参数模板中编码的信息静态创建操作。
我的目标是弥合这两个框架之间的差距。因此,我不能使用硬编码的解决方案。
编辑 2
我发现这个question 有同样的问题和一个很好的答案,它非常接近T.C.'s one(使用指针)。 extern 链接也很重要。
但是,我意识到我忘记了一个关键元素。我的bool 数组包含在matrix 结构中,以便能够重载运算符^、| 等:
template <std::size_t N>
struct matrix
{
const bool data_[N*N];
template<typename... Values>
constexpr matrix(Values... values) noexcept
: data_{static_cast<bool>(values)...}
{}
constexpr bool operator [](std::size_t index) const noexcept
{
return data_[index];
}
}
因此,如果我们应用 T.C 的解决方案:
template<std::size_t N, const bool (&Tab)[N], class>
struct ty1_helper;
template<std::size_t N, const bool (&Tab)[N], std::size_t... Is>
struct ty1_helper<N, Tab, std::index_sequence<Is...>>
{
using type = foo<Tab[Is]...>;
};
template<std::size_t N, const bool (&Tab)[N]>
using ty1 = typename ty1_helper<N, Tab, std::make_index_sequence<N>>::type;
编译器抱怨传递非类型参数:
// error: non-type template argument does not refer to any declaration
// using t = make_output_template<m.data_, std::make_index_sequence<3>>;
// ^~~~~~~
using t = ty1<3, m.data_>;
【问题讨论】:
-
你想推多远?可以硬编码
tab及其大小还是想要更通用的东西? -
您使用哪种语言? C++11 还是 C++14? (对我来说,它看起来很像后者......)
-
您在寻找the indices trick吗?
-
@LightnessRacesinOrbit 我在此示例中使用 C++14 来简化索引的创建,但它可以在 C++11 中使用适当的替换。