如何通过C++元函数实现多个自定义vec模板的逐元素乘积运算
实现方案
我们可以基于C++17的折叠表达式+索引序列实现需求,代码如下:
首先是已知的vec模板定义:
template<int... elements> struct vec;
完整实现代码
#include <utility> #include <cstddef> // 辅助元函数:获取vec的长度 template<typename Vec> struct get_vec_len; template<int... Els> struct get_vec_len<vec<Els...>> { static constexpr std::size_t value = sizeof...(Els); }; // 辅助元函数:获取vec第I个位置的元素值 template<std::size_t I, typename Vec> struct get_element; template<std::size_t I, int First, int... Rest> struct get_element<I, vec<First, Rest...>> { static constexpr int value = get_element<I-1, vec<Rest...>>::value; }; template<int First, int... Rest> struct get_element<0, vec<First, Rest...>> { static constexpr int value = First; }; // 主模板声明 template<typename ...AllVecs> struct multiVecs; // 偏特化匹配所有vec参数的场景 template<int... FirstEls, typename... RestVecs> struct multiVecs<vec<FirstEls...>, RestVecs...> { private: static constexpr std::size_t vec_len = sizeof...(FirstEls); // 类型校验:判断是否为vec实例 template<typename T> static constexpr bool is_vec = false; template<int... Els> static constexpr bool is_vec<vec<Els...>> = true; // 入参合法性校验 static_assert((is_vec<RestVecs> && ...), "所有入参必须是vec类型实例"); static_assert((get_vec_len<RestVecs>::value == vec_len && ...), "所有入参vec的长度必须一致"); // 索引展开辅助:逐位置计算乘积 template<std::size_t... I> static constexpr auto calc(std::index_sequence<I...>) -> vec<(get_element<I, vec<FirstEls...>>::value * ... * get_element<I, RestVecs>::value)...>; public: using type = decltype(calc(std::make_index_sequence<vec_len>{})); }; // 便捷使用别名 template<typename... AllVecs> using multiVecs_t = typename multiVecs<AllVecs...>::type;
效果验证
对题目给出的示例:
using result = multiVecs_t<vec<0,1,2>, vec<1,2,3>, vec<2,3,4>>;
最终result的类型就是vec<0, 6, 24>,和预期结果一致。
内容的提问来源于stack exchange,提问作者ATK
相关产品推荐
相关产品推荐

