zoukankan      html  css  js  c++  java
  • 类的成员函数指针和mem_fun适配器的用法

    先来看一个最简单的函数:

    void foo(int a)
    {
        cout << a << endl;
    }

    它的函数指针类型为

    void (*)(int);

    我们可以这样使用:

    void (*pFunc)(int) = &foo;
    pFunc(123);

    这就是函数指针的基本使用。

    类的成员函数

    那么,对于类的成员函数,函数指针有什么不同呢?

    我们观察下面的类:

    class Foo
    {
    public:
    
        //void (Foo::*)(int)
        void foo(int a)
        {
            cout << a << endl;
        }
    
        //void (*)(int)
        static void bar(int a)
        {
            cout << a << endl;
        }
    };

    我们尝试使用:

    void (*pFunc)(int) = &Foo::foo;

    得到编译错误:

    error: cannot convert ‘void (Foo::*)(int)’ to ‘void (*)(int)’ in initialization

    从上面的编译错误,我们可以得知,foo的函数指针类型绝对不是我们期望的void (*)(int),而是void (Foo::*)(int)。

    原因很简单,类的成员函数,含有一个隐式的参数this,所以foo实际是存在两个参数,Foo*和int。

    那么我们尝试使用void (Foo::*)(int)类型,如下:

    void (Foo::*pFunc2)(int) = &Foo::foo;

    那么如何调用呢,我们采用下列两种方式:

    Foo f;
    (f.*pFunc2)(45678);

    以及

    Foo *pf = &f;
    (pf->*pFunc2)(7865);

    此时的使用方式是正确的。

    那么bar函数是static函数,它具有什么特点呢?

    void (*pFunc)(int) = &Foo::bar;
     pFunc(123);

    我们发现,static函数和自由函数的指针类型一致。

    既然foo含有一个隐式参数,那么能否将其转化出来呢?我们使用STL中的mem_fun,这是一种函数适配器。

    Foo f;
    //void (Foo::*)(int) -> void (*)(Foo*, int)
    (mem_fun(&Foo::foo))(&f, 123);

    我们可以看到,mem_func起到一种转化作用,将void (Foo::*)(int)类型的成员函数指针转化为void (*)(Foo*, int),后者是一个自由函数类型的指针,可以自由调用。

    完毕。

  • 相关阅读:
    CodeForces 288A Polo the Penguin and Strings (水题)
    CodeForces 289B Polo the Penguin and Matrix (数学,中位数)
    CodeForces 289A Polo the Penguin and Segments (水题)
    CodeForces 540C Ice Cave (BFS)
    网站后台模板
    雅图CAD
    mbps
    WCF学习-协议绑定
    数据库建表经验总结
    资源位置
  • 原文地址:https://www.cnblogs.com/inevermore/p/4014429.html
Copyright © 2011-2022 走看看