std::bind 用于绑定一个已有的函数,返回一个新的可调用对象,可以在绑定时改变参数的顺序和个数,生成一种新的调用方式。

std::function 用于构造一个统一的函数对象,特别适合用作回调函数,用来替代传统的函数指针,常常和匿名函数(lambda)配合使用。

示例代码

下面这段示例演示了 std::bind 与 std::function 的几种典型用法,包括参数绑定、参数顺序调换、函数对象替代函数指针,以及 std::function 持有 bind 结果等场景。

#include<iostream>
                
                
                #include "functional"
                
                using namespace std;
                
                double calculate(double x, double y, char op)
                {
                	switch (op)
                	{
                
                	case  '+':
                	{
                				 return x + y;
                	}break;
                
                	case  '-':
                	{
                				 return x - y;
                	}break;
                	}
                	return 0;
                }
                
                
                int main()
                {
                
                
                	//bind
                	auto plus = std::bind(calculate, std::placeholders::_1, std::placeholders::_2, '+');/*calculate 参数1 参数2*/
                	auto sub = std::bind(calculate, std::placeholders::_2, std::placeholders::_1, '-');/*calculate 参数2 参数1*/
                	cout << plus(5, 2) << endl;
                	cout << sub(5, 2) << endl;/*调用时候 5为 calculate的第二个参数*/
                
                
                	//function
                	typedef	std::function<double(double , double , char)> func;
                	func fun = calculate;
                	cout << fun(1, 2, '+') << endl;;
                
                	//function ptr
                	 double (*p)(double, double, char) =calculate;
                	 cout << p(1, 1, '+') << endl;;
                
                
                	//function + bind
                	std::function<double (double , double )> plus_2;
                	plus_2 = plus;
                	cout << plus_2(2, 3) << endl;;
                
                	system("pause");
                	return 0;
                
                }

要点说明

  • std::bind(calculate, _1, _2, '+') 把 calculate 的第三个参数固定为 '+',调用时只需要传入前两个参数,就得到一个加法函数对象。
  • std::bind(calculate, _2, _1, '-') 利用占位符交换了前两个参数的顺序,调用 sub(5, 2) 时,5 实际上作为 calculate 的第二个参数传入。
  • std::function<double(double, double, char)> 可以直接由普通函数 calculate 赋值构造,调用方式与原函数一致。
  • 同样的功能也可以用传统的函数指针 double (*p)(double, double, char) 来实现,std::function 在类型描述和可扩展性上更为通用。
  • std::function 也可以持有 std::bind 的结果,例如将上面绑定好的 plus 赋值给 std::function<double(double, double)>,从而得到一个签名更简洁的函数对象。