I was recently on an interview for a position where C/C++ is the primary language and during one question I was told that it's possible to use the vtable to determine which class in a hierarchy a base pointer actually stores.
So if, for example you have
class A
{
public:
A() {}
virtual ~A() {}
virtual void method1() {}
};
class B : public A
{
public:
B() {}
virtual ~B() {}
virtual void method1() {}
};
and you instantiate A * pFoo = new B()
, is it indeed possible to use the vtable to determine whether pFoo contains a pointer to an instance of A or B?
This is obviously implementation dependent but, on most implementations, the in-memory representation of an object of class A
or B
will start with a pointer to the vtable. You can look at this vtable pointer, compare it to vtable pointers for objects that you know to be of class A
or B
, and determine the class of the object in that way.
To illustrate (of course this is anything but good style):
A *pFoo=new B(); // pointer to object of unknown class (either A or B)
A a; // Object known to be of class A
B b; // Object known to be of class B
void *vptrA=*((void **)&a); // Pointer to vtable of class A
void *vptrB=*((void **)&b); // Pointer to vtable of class B
void *vptrFoo=*((void **)pFoo); // Pointer to vtable of unknown object
if(vptrFoo==vptrA)
printf("Class A\n");
else
printf("Class B\n");
Important: This is only an illustration of how most implementations work; besides being implementation dependent, this technique breaks down in the presence of multiple inheritance. You should never do anything like this in production code; use RTTI instead.
Yes, it's quite possible to do - use dynamic_cast. This is pretty crappy question - a slightly better one might be "How is dynamic_cast implemented?" but really if asked either at an interview I'd have to wonder about the nous of the interviewer. Being a good, or even a great, C++ programmer does not depend on knowing nitpicking implementation details like this, but these are of course easy questions for second-raters to ask.
Check the typeid() function.
You can access vpointer and even you can call any virtual method in class through vpointer.
But remember this is EVIL.
Example :
class A
{
public:
void f1()
{
cout<<"bbb"<<endl;;
}
virtual void f2()
{
cout<<"ccc"<<endl;;
}
virtual void f3()
{
cout<<"ddd"<<endl;;
}
};
and call in main
A a;
typedef void (__thiscall* foo)();
(*(foo)((void**)(((void**)(&a))[0]))[1])();
It will access vpointer and then will go by index and will execute the second method in vTable which is f3().
Also note to use RTTI as already suggested.