【C++ 学习 ㉞】- C++11 的包装器和绑定器

目录

一、可调用对象

二、包装器

三、绑定器


 


一、可调用对象

对于一个对象或者表达式,如果可以对其使用调用运算符 (),则称它为可调用对象

一般来说,可调用对象归类为以下几种:

  1. 普通函数

  2. 函数指针

  3. 类的静态成员函数

  4. 类的非静态成员函数

  5. 函数对象(又称仿函数)

  6. lambda 表达式

#include 
#include 
using namespace std;
​
int add(int x, int y)
{
    return x + y;
}
​
class Sub
{
public:
    static int sub(int x, int y)
    {
        return x - y;
    }
};
​
class Mul
{
public:
    int mul(int x, int y)
    {
        return x * y;
    }
};
​
struct Div
{
    int operator()(int x, int y)
    {
        return x / y;
    }
};
​
int main()
{
    cout << add(10, 5) << endl;  // 普通函数
    int(*fp1)(int, int) = add;
    cout << fp1(10, 5) << endl;  // 函数指针
​
    cout << Sub::sub(10, 5) << endl;  // 类的静态成员函数
    int(*fp2)(int, int) = Sub::sub;
    cout << fp2(10, 5) << endl;
​
    Mul obj;
    cout << obj.mul(10, 5) << endl;  // 类的非静态成员函数
    int(Mul:: * fp3)(int, int) = &Mul::mul;
    cout << (obj.*fp3)(10, 5) << endl;
​
    Div div1;  
    cout << div1(10, 5) << endl;  // 函数对象(又称仿函数)
    auto div2 = [](int x, int y) { return x / y; }; 
    cout << div2(10, 5) << endl;  // lambda 表达式
    return 0;
}

在上面的例子中,满足条件的这些可调用对象对应的类型被统称为可调用类型。

C++ 中的可调用类型虽然具有比较统一的操作形式,但定义的方式五花八门,这样在我们试图使用统一的方式保存,或者传递一个可调用对象时会十分繁琐

现在,C++11 通过提供包装器 std::function绑定器 std::bind 统一了可调用对象的各种操作,就如同秦始皇统一六国后,实行了书同文、车同轨、度同制。


二、包装器

std::function 类模板是一个通用的可调用对象的包装器

template  function;     // undefined
template  class function;
// Ret:返回值类型
// Args...:形参类型列表

下面我们用包装器来包装上文中的可调用对象

#include 
#include 
using namespace std;
​
int main()
{
    function f1 = add;
    cout << f1(10, 5) << endl;
​
    function f2 = Sub::sub;
    cout << f2(10, 5) << endl;
​
    function f3 = &Mul::mul;
    cout << f3(Mul(), 10, 5) << endl;
​
    function f4 = Div();
    cout << f4(10, 5) << endl;
​
    function f5 = [](int x, int y) { return x / y; };
    cout << f5(10, 5) << endl;
    return 0;
}

通过上述示例代码,我们可以发现:

  1. 除了类的非静态成员函数,其他的可调用对象通过包装器的包装,得到了一个统一的格式,包装完成得到的对象相当于一个函数指针,和函数指针的使用方式相同,通过包装器对象就可以完成对包装的函数的调用了

  2. 类的非静态成员函数还需要传入 this 指针,所以单独使用 std::function 是不够的,还需要结合使用 std::bind 函数绑定 this 指针以及参数列表


三、绑定器

std::bind 函数模板是一个通用的函数适配器(绑定器),它用一个可调用对象及其参数,生成一个新的可调用对象,以适应模板

现在我们使用绑定器将类的非静态成员函数统一格式

#include 
#include 
using namespace std;
​
int main()
{
    function f = bind(&Mul::mul, Mul(), placeholders::_1, placeholders::_2);
    cout << f(10, 5) << endl;
    return 0;
}

你可能感兴趣的:(C++,c++,学习,开发语言)