Is it legal to cast a pointer-to-member-function to another pointer-to-member-function of the same class using reinterpret_cast
? The following example works. But is it legal?
#include<iostream>
#include<vector>
#include<string>
class A
{
public:
void func_int(int x) { std::cout << x << std::endl; }
void func_string(std::string const& x) { std::cout << x << std::endl; }
};
int main()
{
std::vector<void(A::*)()> v;
v.push_back(reinterpret_cast<void(A::*)()>(&A::func_int));
v.push_back(reinterpret_cast<void(A::*)()>(&A::func_string));
A a;
(a.*reinterpret_cast<void(A::*)(int)>(v[0]))(5);
(a.*reinterpret_cast<void(A::*)(std::string const&)>(v[1]))(std::string{"Test"});
return 0;
}
At [expr.reinterpret.cast] the C++ draft states:
A prvalue of type “pointer to member of
X
of typeT1
” can be explicitly converted to a prvalue of a different type “pointer to member ofY
of typeT2
” ifT1
andT2
are both function types or both object types.72 The null member pointer value ([conv.mem]) is converted to the null member pointer value of the destination type. The result of this conversion is unspecified, except in the following cases:
converting a prvalue of type “pointer to member function” to a different pointer to member function type and back to its original type yields the original pointer to member value.
converting a prvalue of type “pointer to data member of
X
of typeT1
” to the type “pointer to data member ofY
of typeT2
” (where the alignment requirements ofT2
are no stricter than those ofT1
) and back to its original type yields the original pointer to member value.
72)
T1
andT2
may have different cv-qualifiers, subject to the overall restriction that areinterpret_cast
cannot cast away constness.
Since you are converting your "pointer to member function" to a different "pointer to member function" type and back, it yields the original value. This is both legal and well-defined behaviour. So your code should work properly.