How to implement operator == for polymorphic classes in C ++

Possible duplicate:
What is the correct way to overload operator == for a class hierarchy?

I have a base class and several derived classes, as in the following code:

class Base { public: friend bool operator==(const Base&, const Base&); virtual ~Base(){} private: virtual bool equals(const Base& other) const = 0; }; bool operator==(const Base& lhs, const Base& rhs) { return lhs.equals(rhs); } class A : public Base { public: A(int x) : x_(x){} private: virtual bool equals(const Base& other) const; int x_; }; bool A::equals(const Base& other) const { const A* pA = dynamic_cast<const A*>(&other); if(!pA) return false; return x_ == pA->x_; } class B : public Base { public: B(double y) : y_(y){} private: virtual bool equals(const Base& other) const; double y_; }; bool B::equals(const Base& other) const { const B* pB = dynamic_cast<const B*>(&other); if(!pB) return false; return y_ == pB->y_; } 

To be able to compare two derived classes, I want to have the == operator. The question is how to achieve this in an object-oriented way (for example, taking into account encapsulation, maintainability and extensibility). Are there any recommended patterns for this? Is there an alternative to the above approach that does not allow dynamic_cast?

+6
source share
1 answer

Your path is not perfect. Consider the following class derived from A :

 class AA : public A { public: AA(int x, int y) : A(x), y_(y) {} private: virtual bool equals(const Base& other) const; int y_; }; bool AA::equals(const Base& other) const { const AA* pAA = dynamic_cast<const AA*>(&other); if(!pAA) return false; return A::equals(other) && y_ == pAA->y_; } 

then your operatator == violates the basic rule, this is not a symmetric relation:

  A a(1); AA aa(1,1); assert(a == aa); assert(!(aa == a)); 

A short fix will be to use typeid :

 bool operator==(const Base& lhs, const Base& rhs) { return typeid(lhs) == typeid(rhs) && lhs.equals(rhs); } 
+3
source

All Articles