为什么指向非const成员函数的指针不能指向const成员函数而相反?

pku*_*bik 8 c++ pointers const function-pointers

指向成员函数的指针是什么原因,不能指向const成员函数?

struct A {
    void g() {};
    void f() const {}
};
Run Code Online (Sandbox Code Playgroud)

后来的代码:

void (A::* fun)() = &A::f;
Run Code Online (Sandbox Code Playgroud)

此代码生成:

error: cannot convert ‘void (A::*)()const’ to ‘void (A::*)()’ in initialization
Run Code Online (Sandbox Code Playgroud)

当然它编译&A::g而不是&A::f.

相反的情况:

void (A::* fun)() const = &A::g;
Run Code Online (Sandbox Code Playgroud)

错误是:

error: cannot convert ‘void (A::*)()’ to ‘void (A::*)()const’ in initialization
Run Code Online (Sandbox Code Playgroud)

第二种情况相当清楚.const指针不应该修改对象,因此它不能保存执行它的功能.但是为什么不能像第一种情况那样将const成员函数分配给成员函数non-const

它看起来像正常的指针,其中铸造规则const,以non-const允许修改的价值,但我不认为这里的点,其中常量,正确性在函数定义检查,这样的分配之前.

Sho*_*hoe 5

为什么指向成员函数的指针不能指向const成员函数?

因为修饰符是函数签名const的一部分。一旦声明了函数指针,该函数指针只能用于将指针分配给具有相同函数签名的函数。


小智 3

非静态成员函数有一个额外的隐藏this参数。鉴于该额外隐藏参数的存在,非静态的void A::f() const;行为非常类似于void A__f(const A *__this),并且您看到的成员函数的行为模拟了非成员函数的行为。

void f(void *);
void (*pf)(const void *) = f; // also an error
Run Code Online (Sandbox Code Playgroud)

至于它是否会在任何实现上中断,我认为理论上,允许实现void *从与参数不同的寄存器读取参数const void * ,如果是这样,则转换的结果(如果有效)不能用于正确调用f。我不知道为什么任何实施者会做出这样的决定,我也不知道有任何真正的实施这样做,但这是标准允许的。