InQusitive InQusitive - 16 days ago 5
C++ Question

Best approach for avoiding repetitive dynamic_cast?

I have a situation like

Shape *shape =dynamic_cast<Shape*>(obj);

if(dynamic_cast<Rectangle*>(obj))
{
func();
Rectangle* obj1 = dynamic_cast<Rectangle*>(obj);
obj1->DoSomething1();
obj1->DoSomething2();
}
else if(dynamic_cast<Circle*>(obj))
{
func();
Cirlce* obj2 = dynamic_cast<Cirlce*>(obj);
obj1->DoSomething3();
obj1->DoSomething4();
}
else if(dynamic_cast<Blah*>(obj))
{
func();
Blah* obj1 = dynamic_cast<Blah*>(obj);
obj1->DoSomething5();
obj1->DoSomething6();
}
...
...


What is the best approach for avoiding calling the
dynamic_cast
again inside a
if/else
statement and execute a method for that particular object type?

Answer

In general, you should avoid such constructs and utilitize polymorphism the way it was intended to be used, eg:

class Shape
{
public:
    virtual void DoSomething() = 0;
};

class Rectangle : public Shape
{
public:
    void DoSomething()
    {
        DoSomething1();
        DoSomething2();
    }
};

class Circle : public Shape
{
public:
    void DoSomething()
    {
        DoSomething3();
        DoSomething4();
    }
};

class Blah : public Shape
{
public:
    void DoSomething()
    {
        DoSomething5();
        DoSomething6();
    }
};

Shape *shape = dynamic_cast<Shape*>(obj);
if (shape)
{
    func();
    shape->DoSomething(); 
}

If that is not an option for your code, you can do the following to remove the duplicate dynamic_cast calls, at least:

if (Rectangle *r = dynamic_cast<Rectangle*>(obj))
{
    func();
    r->DoSomething();
}
else if (Circle *c = dynamic_cast<Circle*>(obj))
{
    func();
    c->DoSomethingElse();
}
else if (Blah *b = dynamic_cast<Blah*>(obj))
{
    func();
    b->DoSomethingElseElse();
}