C++ 为什么指向非常量成员函数的指针可以';t点常量成员函数和相反?

C++ 为什么指向非常量成员函数的指针可以';t点常量成员函数和相反?,c++,pointers,constants,function-pointers,C++,Pointers,Constants,Function Pointers,指向成员函数的指针不能指向常量成员函数的原因是什么 struct A { void g() {}; void f() const {} }; 后面的代码: void (A::* fun)() = &A::f; 此代码生成: error: cannot convert ‘void (A::*)()const’ to ‘void (A::*)()’ in initialization 当然,它是用&A::g而不是&A::f编译的 在相反的情况下: void (A::*

指向成员函数的指针不能指向常量成员函数的原因是什么

struct A {
    void g() {};
    void f() const {}
};
后面的代码:

void (A::* fun)() = &A::f;
此代码生成:

error: cannot convert ‘void (A::*)()const’ to ‘void (A::*)()’ in initialization
当然,它是用
&A::g
而不是
&A::f
编译的

在相反的情况下:

void (A::* fun)() const = &A::g;
错误是:

error: cannot convert ‘void (A::*)()’ to ‘void (A::*)()const’ in initialization
第二种情况相当清楚
const
指针不应修改对象,因此它不能保存执行该操作的函数。但是为什么不能像第一种情况那样将
const
成员函数分配给
non-const
成员函数呢

它看起来像是普通指针的规则,其中将
const
转换为
non-const
将允许修改值,但我看不到这里的点,在这样的赋值之前,在函数定义中检查const正确性

指向成员函数的指针不能指向常量成员函数的原因是什么

struct A {
    void g() {};
    void f() const {}
};

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

非静态成员函数有一个额外的隐藏
参数。考虑到这个额外隐藏参数的存在,一个非静态的
void a::f()常量
的行为非常类似于
void A\u f(const A*\u this)
,您看到的成员函数的行为模拟了非成员函数的行为

void f(void *);
void (*pf)(const void *) = f; // also an error

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

从语义上讲,你是正确的,没有问题。原则上,接受
(常量Foo*x,常量Bar*y)
的函数可以转换为接受
(Foo*x,Bar*y)
的函数,而不存在违反常量正确性的风险。但是,正如答案所说,在C++中,这些<代码> const 声明是函数签名的一部分,它用于过载解决、名称篡改等,因此语言禁止。