C ++成员函数指针定义

交火

考虑以下代码:

#include <iostream>
#include <functional>

struct B {
    template <class C, class M, class T>
    void call1(C (M::*member)(), T *instance) {
        std::function<void()> fp = std::bind(member, instance);
        fp();
    }

    template <class C, class M, class T>
    void call2(C (M::*member), T *instance) {
        std::function<void()> fp = std::bind(member, instance);
        fp();
    }

    void foo() {
        call1(&B::func, this); // works
        call2(&B::func, this); // works

        call1(&B::func2, this); // Error: no matching member function for call to 'call2'
        call2(&B::func2, this); // works
    }

    void func() {
        std::cout << "func\n";
    }

    void func2() const volatile {
        std::cout << "func2\n";
    }
};

int main() {
    B{}.foo();
}

似乎更高的版本不接受带有额外的cv限定词的功能。

这样指定函数成员指针C (M::*member)()和这样指定函数成员指针有什么区别C (M::*member)

巴里

让我们简化为仅考虑以下两者之间的区别:

template <class C, class M> void f(C (M::*member)());
template <class C, class M> void g(C (M::*member));

在中fmember是指向M返回零值并返回的成员函数的指针C如果使用调用&B::func,编译器将推导M == BC == void直截了当。

在中gmember只是一个指向Mtype成员的指针C但是,就我们而言,&B::func是一个函数。因此,这里的影响只是放下了指针。我们M == B再次推断出,而C变为void()-现在C是一个函数类型。这是不那么专业的版本,f因为它允许更多类型的成员。g可以与带有参数的函数,与成员的指针匹配,或者与cv限定的成员functinos匹配。

让我们以一个重载函数为例,以及如何对其进行不同的推导(这是您问题中的原始问题,此问题已被编辑,但仍然很有趣):

struct X {
    void bar() { }
    void bar(int ) { }
};

当我们这样做时:

f(&X::bar);

即使&X::bar是一个重载的名称,实际上也只有一个匹配C (M::*)()具有M == X和的那个C == void我们根本没有办法过载bar服用int模板类型相匹配。因此,这是传递重载名称的可接受用途之一。这会导致罚款。

但是,当我们这样做时:

g(&X::bar);

现在,有两个完全有效的推论。C可能是void()void(int)由于两者都是有效的,因此推论是模棱两可的,并且您无法编译-并没有真正使这一点特别清楚的错误。


现在回到您的示例:

call1(&B::func2, this); // Error: no matching member function for call to 'call2'
call2(&B::func2, this); // works

的类型&B::func2void (B::*)() const volatile由于call1推导不带参数且不具备cv资格的成员函数类型,因此类型推导只会失败。没有C没有M要匹配的类型。

但是,这种call2推论很好,因为它更通用。它可以匹配任何指向成员的指针。我们最终以结束C = void() const volatile这就是为什么这样。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

如何将(非静态成员函数的)C ++函数指针传递给预定义的C函数?

来自分类Dev

C ++开关与成员函数指针与虚拟继承

来自分类Dev

C ++将指针传递给非静态成员函数

来自分类Dev

调用成员指针函数C ++

来自分类Dev

将成员函数指针传递给C样式函数

来自分类Dev

来自其他类的C ++成员函数指针

来自分类Dev

指向具有多个对象的成员函数的指针的向量C ++

来自分类Dev

C ++ const成员函数返回一个指针

来自分类Dev

成员函数指针的decltype作为c ++ 11中的模板参数

来自分类Dev

C ++是否有定义的方法将指针传递给类的成员对象的成员函数?

来自分类Dev

成员函数的C ++条件模板类定义

来自分类Dev

如何重新定义C ++指针函数?

来自分类Dev

C ++:如何返回指向非静态成员函数的指针?

来自分类Dev

是否在C ++中定义了对空指针的成员访问?

来自分类Dev

在类定义C ++之前使用类成员函数指针

来自分类Dev

使用成员函数指针作为键的C ++映射问题

来自分类Dev

C ++ typedef函数定义为类成员,以后用作函数指针吗?

来自分类Dev

调用成员指针函数C ++

来自分类Dev

FSM在C ++中使用成员函数指针

来自分类Dev

不同类的成员函数指针的C ++映射

来自分类Dev

C ++,模板或指向成员函数的指针

来自分类Dev

成员函数指针c ++

来自分类Dev

C ++ const成员函数返回一个指针

来自分类Dev

指向成员函数的C ++指针出错:不是函数或函数指针

来自分类Dev

C ++-无法修改类成员函数中的指针

来自分类Dev

成员函数指针的decltype作为c ++ 11中的模板参数

来自分类Dev

指向成员函数的C ++指针而不是函数指针

来自分类Dev

指向类成员的 C++ 函数指针

来自分类Dev

使函数指针成为c中结构的成员

Related 相关文章

  1. 1

    如何将(非静态成员函数的)C ++函数指针传递给预定义的C函数?

  2. 2

    C ++开关与成员函数指针与虚拟继承

  3. 3

    C ++将指针传递给非静态成员函数

  4. 4

    调用成员指针函数C ++

  5. 5

    将成员函数指针传递给C样式函数

  6. 6

    来自其他类的C ++成员函数指针

  7. 7

    指向具有多个对象的成员函数的指针的向量C ++

  8. 8

    C ++ const成员函数返回一个指针

  9. 9

    成员函数指针的decltype作为c ++ 11中的模板参数

  10. 10

    C ++是否有定义的方法将指针传递给类的成员对象的成员函数?

  11. 11

    成员函数的C ++条件模板类定义

  12. 12

    如何重新定义C ++指针函数?

  13. 13

    C ++:如何返回指向非静态成员函数的指针?

  14. 14

    是否在C ++中定义了对空指针的成员访问?

  15. 15

    在类定义C ++之前使用类成员函数指针

  16. 16

    使用成员函数指针作为键的C ++映射问题

  17. 17

    C ++ typedef函数定义为类成员,以后用作函数指针吗?

  18. 18

    调用成员指针函数C ++

  19. 19

    FSM在C ++中使用成员函数指针

  20. 20

    不同类的成员函数指针的C ++映射

  21. 21

    C ++,模板或指向成员函数的指针

  22. 22

    成员函数指针c ++

  23. 23

    C ++ const成员函数返回一个指针

  24. 24

    指向成员函数的C ++指针出错:不是函数或函数指针

  25. 25

    C ++-无法修改类成员函数中的指针

  26. 26

    成员函数指针的decltype作为c ++ 11中的模板参数

  27. 27

    指向成员函数的C ++指针而不是函数指针

  28. 28

    指向类成员的 C++ 函数指针

  29. 29

    使函数指针成为c中结构的成员

热门标签

归档