nor*_*ner 8 c++ function parameter-passing
I have the situation where one function calls one of several possible functions. This seems like a good place to pass a function as a parameter. In this Quoara answer by Zubkov there are three ways to do this.
int g(int x(int)) { return x(1); }
int g(int (*x)(int)) { return x(1); }
int g(int (&x)(int)) { return x(1); }
...
int f(int n) { return n*2; }
g(f); // all three g's above work the same
Run Code Online (Sandbox Code Playgroud)
When should which method be used? What are there differences? I prefer the simplest approach so why shouldn't the first way always be used?
For my situation, the function is only called once and I'd like to keep it simple. I have it working with pass by pointer and I just call it with g(myFunc)
where myFunc
is the function that gets called last.
扩展 LF 的评论,通常最好完全避开函数指针,并根据可调用对象(定义的事物operator()
)进行工作。以下所有内容都允许您执行此操作:
#include <type_traits>
// (1) unrestricted template parameter, like <algorithm> uses
template<typename Func>
int g(Func x) { return x(1); }
// (2) restricted template parameter to produce possibly better errors
template<
typename Func,
typename=std::enable_if_t<std::is_invocable_r_v<int, Func, int>>
>
int g(Func x) { return std::invoke(x, 1); }
// (3) template-less, trading a reduction in code size for runtime overhead and heap use
int g(std::function<int(int)> x) { return x(1); }
Run Code Online (Sandbox Code Playgroud)
重要的是,所有这些都可以在带有捕获的 lambda 函数上使用,这与您的任何选项不同:
int y = 2;
int ret = g([y](int v) {
return y + v;
});
Run Code Online (Sandbox Code Playgroud)