C++ 带空参数包的一元折叠
问题是,当使用空扩展指定折叠表达式时,C++ 带空参数包的一元折叠,c++,variadic-templates,c++20,fold,C++,Variadic Templates,C++20,Fold,问题是,当使用空扩展指定折叠表达式时,(…*items)在编译时无效;即使在运行时也不会对其进行评估 您可以使用(从C++17开始);然后,当使用空展开指定折叠表达式时,else部分将被丢弃 如果值为true,则放弃语句false(如果存在),否则放弃语句true 模板 constexpr std::size\u t count() { 返回std::index_sequence().size(); } 模板 constexpr std::size\u t fold\u mul() { 如果co
(…*items)
在编译时无效;即使在运行时也不会对其进行评估
您可以使用(从C++17开始);然后,当使用空展开指定折叠表达式时,else部分将被丢弃
如果值为true,则放弃语句false(如果存在),否则放弃语句true
模板
constexpr std::size\u t count()
{
返回std::index_sequence().size();
}
模板
constexpr std::size\u t fold\u mul()
{
如果constexpr(count()==0)
// ^^^^^^^^^
{
返回1;
}
其他的
{
退货(……*项);
}
}
对于空序列,唯一具有默认值的折叠表达式是&
(默认为true
)、|
(默认为false
)和,
(默认为void()
)
就语言而言,*
没有默认值。但在这种情况下,我们可以使用二元折叠而不是一元折叠:
模板
constexpr std::size\u t fold\u mul()
{
退货(1*…*项);
}
这适用于空的情况(值仅为
1
)和非空的情况(因为1
是乘法的标识元素,所以不会更改值)。非常整洁,我以前不知道这一点!或者简单地返回(1*…*项)
:-)您知道您可以简单地使用sizeof…(Args)
来获取Args
的长度吗?
#include <iostream>
#include <utility>
template<std::size_t... items>
constexpr std::size_t count()
{
return std::index_sequence<items...>().size();
}
template<std::size_t... items>
constexpr std::size_t fold_mul()
{
if( count<items...>() == 0 )
{
return 1;
}
else
{
return (... * items);
}
}
int main()
{
std::cout << "Result: " << fold_mul<>() << "\n";
}
template<typename... Args>
constexpr std::size_t fold_mul();
template<std::size_t... j>
requires (count<j...>() > 0)
constexpr std::size_t fold_mul()
{
return (j * ...);
}
template<>
constexpr std::size_t fold_mul()
{
return 1;
}
template<std::size_t... items>
constexpr std::size_t count()
{
return std::index_sequence<items...>().size();
}
template<std::size_t... items>
constexpr std::size_t fold_mul()
{
if constexpr ( count<items...>() == 0 )
// ^^^^^^^^^
{
return 1;
}
else
{
return (... * items);
}
}