我想编写一个函数来接受任意数量的数字参数并返回它们的均值。使用Wikipedia的扩展技巧:
namespace detail
{
template<typename... Args> void iterate_template_pack(Args&&...) {}
}
template <typename ResultType, typename... Args>
ResultType arithmeticMean(Args&&... args)
{
ResultType acc = ResultType(0);
size_t n = 0;
detail::iterate_template_pack(([&](){
acc += ResultType(args);
++n;
})...);
return acc / n;
}
这编译并且几乎可以工作:我可以正确地看到lambda接收args。但是,acc
和n
不会被修改。怎么样?
答案 0 :(得分:4)
你需要调用lambda,否则你只是将一系列lambda对象传递给iterate_template_pack
:
detail::iterate_template_pack(([&](){
acc += ResultType(args);
++n;
})()...);
^^
由于你的lambda没有返回值,你还需要提供一个传递给iterate_template_pack
的值,因为你不能将void
作为参数传递:
detail::iterate_template_pack((([&](){
acc += ResultType(args);
++n;
})(), void(), 0)...);
From Wikipedia(我的重点):
可以指定一个lambda表达式并执行就地,而不是执行一个函数,这样就可以就地执行任意语句序列。
pass{([&]{ std::cout << args << std::endl; }(), 1)...};
请注意,由于PR 47226,gcc无法编译上述内容(另请参阅https://stackoverflow.com/a/13444602/34509)。一种解决方法是在lambda:
之外扩展参数包detail::iterate_template_pack((([&](ResultType&& r){
acc += r;
++n;
}(args)), void(), 0)...);