Let's say I have a pointer type that can hold the address of a base class method. Can I assign the address of a subclass method to it and expect it to work correctly? In my case I'm using it with a base class pointer and the dynamic type of the object is the derived class.
struct B
{
typedef void (B::*MethodPtr)();
};
struct D: public B
{
void foo() { cout<<"foo"<<endl; }
};
int main(int argc, char* argv[])
{
D d;
B* pb = &d;
//is the following ok, or undefined behavior?
B::MethodPtr mp = static_cast<B::MethodPtr>(&D::foo);
(pb->*mp)();
}
The standard says this when talking about static_cast:
5.2.9.9 An rvalue of type “pointer to member of D of type cv1 T” can be converted to an rvalue of type “pointer to member of B of type cv2 T”, where B is a base class (clause 10) of D, if a valid standard conversion from “pointer to member of B of type T” to “pointer to member of D of type T” exists (4.11), and cv2 is the same
cv-qualification as, or greater cv-qualification than, cv1. 63) The null member pointer value (4.11) is converted to the null member pointer value of the destination type. If class B contains the original member, or is a base or derived class of the class containing the original member, the resulting pointer to member points to the original member. Otherwise, the result of the cast is undefined. [Note: although class B need
not contain the original member, the dynamic type of the object on which the pointer to member is dereferenced must contain the original member; see 5.5.]
As always, I'm having such a hard time deciphering the standard. It kinda says that it is ok, but I'm not 100% sure if the above text really applies to the situation in my example code.
See Question&Answers more detail:
os 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…