[英]using a std::function or a forwarding reference as general-purpose callable object input parameter of a higher-order function?
[英]Perfect-forwarding callable objects in higher-order functions
我一直在写这样的高阶函数:
template<typename F, typename... Args>
void doStuff(F f, Args&&... args)
{
// ...
f(std::forward<Args>(args)...);
// ...
}
或者用F&& f
替换F f
F&& f
。
但在我了解了ref-qualifiers(哎哟)之后,情况变得复杂了。 想象一个仿函数类:
struct Foo {
void operator()(...) &;
void operator()(...) &&;
};
然后我之前的doStuff
实现只会调用&
方法,因为参数总是lvalues。
我认为解决这个问题的方法是像这样实现doStuff
:
template<typename F, typename... Args>
void doStuff(F&& f, Args&&... args)
{
// ...
std::forward<F>(f)(std::forward<Args>(args)...);
// ...
}
这也是std::result_of
可能实现的方式 。 我想知道的是,这个实现有什么缺点,即我应该用它替换所有的HOF实现吗?
std::forward
是一个有条件的r值转换,并且这个点像往常一样从死亡对象中偷走了内脏。 在这方面, functors
和其他对象没有区别。 std::forward
与使用std::forward
; 如果你不准备偷走那些胆量,你就不应该。
#include <iostream>
#include <vector>
struct Foo {
std::vector<int> vec = {1,2,3};
std::vector<int>& operator()(...) & {
return vec;
}
std::vector<int> operator()(...) && {
return std::move(vec);
// Clearly, don't rely on 'vec' here...
}
};
Foo getFoo(){
return {};
}
int main() {
auto foo = getFoo();
auto vec1=foo();
auto vec2=getFoo()();
}
显然,不要做这样的事情:
auto vec3 = std::move(foo)();
vec4 = foo();
出于同样的原因。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.