When to use RTTI – Dynamic_cast in C++

When to use RTTI (Run Time Type Information) dynamic_cast in C++ is frequently asked c++ technical interview question. Answer to this question will cover multiple scenarios where we can use dynamic_cast in C++ program.

Answer:

Scenarios – Use of Dynamic_cast in C++ program:

Situation 1- When we need to call a specialized member function of child class that’s not available to the base class in inheritance hierarchy. Polymorphism breaks down here but sometimes we get this situation.  Below, class B contains specialized funcB() function.

class A {
public:	
	virtual void func() { }
};


class B : public A {
public:
	void func()}

	//Specialized function to B class
	void funcB(){}
};

What if we need to call specialized funcB() using base class pointer like below program. Dynamic cast operator, Part of RTTI in C++ comes into picture to type cast from base to child class.

//A* arg: base class pointer that can have
//any child classes object.
void f(A* arg) {
 
//down cast from base pointer to derive pointer
//as, base class pointer does not understand 
//specialized function of derived class.
B* bp = dynamic_cast<B*>(arg);	
 
  if (bp)
  {   	
		bp->func();
		bp->func2();// ok
  }  
  else{
	  //Call respective class function
    arg->func();
  }
};

Situation 2 – We want to override a function from base class that is not virtual and we can’t make it virtual as base class is sitting in a library and it can’t be modified.

So, overriding is not possible. If we use statements for below program, A* ptr = new B(), ptr->func2(); always base call method will be called as its not virtual in base class. But we want to call child class func2() method.

Then we need to use dynamic_cast operator to type cast base pointer to child pointer to call child’s class method.

//We cannot touch base class A but can be inherited. 
class A {
public:	
	virtual void func() { printf("Class A :func()\n"); }
	        void func2(){ printf("Class A :func2()\n"); }//Not virtual 
};


class B : public A {
public:
	void func() { printf("Class B :func()\n"); }

	//Want to override func2 but can't func2 is not virtual in base class.
	
	//if we use base class pointer with B object, base class func2 function will be called.
	
	//Can't make class A:func2 virtual as it is in a library- binary form.
	
	//only option is RTTI to access it via base class pointer in client code.
	void func2(){ printf("Class B :func2()\n"); }
};

Complete Example: Situation-1: Call specialized member function of a child class using dynamic_cast RTTI in C++.
#include
#include
using namespace std;


class A {
public:	
	virtual void func() { printf("Class A :func()\n"); }
};


class B : public A {
public:
	void func() { printf("Class B :func()\n"); }

	//Specialized function to B class
	void funcB(){ printf("Class B :funcB()\n"); }
};

int main()
{
	A* ap = new B();
 	//Call funcB() function of class B using base pointer A
//	ap->funcB();//Compiler error as funcB() is not a member of Animal	

	//Now use dymaic cast to convert base pointer to derived pointer i.e. A to B.
	B* bp = dynamic_cast<B*>(ap);
	
	if (bp)
	{
		bp->funcB();
	}
	

return 0;
}

Complete Example: Situation-2: Call child class method if it is not virtual in base class in C++

#include
#include
using namespace std;


class A {
public:	
	virtual void func() { printf("Class A :func()\n"); }
	        void func2(){ printf("Class A :func2()\n"); }//Not virtual 
};


class B : public A {
public:
	void func() { printf("Class B :func()\n"); }
	
	void func2(){ printf("Class B :func2()\n"); }
};

class C : public A {
public:
	void func() { printf("Class C :func()\n"); }	
};


//-----Client code------
void f(A* arg) {

	//call 
  B* bp = dynamic_cast<B*>(arg);	
 
  //Call Specific class B function.
  if (bp)
  {   	
		bp->func();
		bp->func2();
  }  
  else{
	  //Call respective class function
    arg->func();
  }
};

int main()
{
	A* ap1 = new B(); 
	f(ap1);


	//operate C object
	A* ap2 = new C();
	f(ap2);

return 0;
}

Related Posts