前言
std::function 作为标准库提供的函数指针,使用起来还是比较方便的,不过在使用过程中有一些需要注意的细节,这里做一个简单的记录。
基本使用
- 头文件:
#include <functional>
- 语法:
std::function<return_type(args_type)>
其中return_type 是函数指针的返回值类型,像上面案例中#include <iostream> #include <functional> using namespace std; void func(int i, int g) { int count = 10; while (count > 0) { cout << "func: " << i << " " << g<< endl; sleep(1); } } int main() { std::function<void(int,int)> job = func; job(10,10); return 0; }
func
函数的void
类型。
其中args_type 是函数指针的参数类型,有多个函数参数,就可以有多个数据类型。
函数指针作为参数 需要注意的事项
-
如果直接使用一个已经存在的函数来进行传参数,则需要声明调用者函数参数的
std::function
为const类型。
具体也就是类似 我们使用"dfafasd" 初始化一个void test_string(std::string& res)
引用类型的字符串参数。这个时候因为是引用传递,而传递的时候却没有用变量,而是使用了一个常量,则需要保证这个函数的声明参数中有一个const ,才能将常量数据的地址正确得放在常量区域。即 正确的声明应该如void test_string(const std::string& res)
同理,std::function在使用一个已经存在的函数初始化的时候类似。如下代码是正确的:
void stl_func(const std::function<void(int, int)>& job, int num, int g) { job(num, g); } void func(int i, int g) { int count = 10; while (count > 0) { cout << "func: " << i << " " << g<< endl; sleep(1); } } int main() { stl_func(func,10,1); return 0; }
如果这个时候去掉了
stl_func
函数参数中的 const 声明,则会报如下错误:candidate function not viable: no know conversion from 'void()' to 'std::function<void(int,int)> &' for 1'st argument.
-
使用一个函数指针变量 来进行参数传递,则不需要调用者函数参数的
std::function
为const。
还是如上代码,修改之后:void stl_func(std::function<void(int, int)>& job, int num, int g) { job(num, g); } void func(int i, int g) { int count = 10; while (count > 0) { cout << "func: " << i << " " << g<< endl; sleep(1); } } int main() { std::function<void(int, int)> job = func; // 使用函数指针 变量进行传递就没有问题 stl_func(job, 10, 10); return 0; }
-
在类的成员函数之间 将 std::function 作为参数传递时需要注意 如下使用过程:
#include <iostream> #include <functional> using namespace std; void stl_func_bak(std::function<void()>& job) { job(); } class Cb { public: static void cb_func() { while(1) { cout << "cb_func: " << 10 << endl; usleep(100000); } } void stl_cb_func() { // 函数成员作为传递的参数需要确保编译期间就能够分配好函数内存 // 函数栈需要在编译期间获得内存,所以需要声明 cb_func 成员函数 为 static stl_func_bak(Cb::cb_func); } }; int main() { Cb* cb = new Cb(); cb->stl_cb_func(); return 0; }
欢迎大家补充使用过程中遇到的问题