Trouble with inheritance of operator= in C++

abstract-class, c++, inheritance, operator-keyword

Solution

If you do not declare copy-assignment operator in a class, the compiler will declare one for you implicitly. The implicitly declared copy-assignment operator will hide any inherited assignment operators (read about "name hiding" in C++), meaning that any inherited assignment operators will become "invisible" to the unqualified name lookup process (which is what happens when you do `b = c`), unless you take specific steps to "unhide" them.

In your case, class `B` has no explicitly declared copy-assignment operator. Which mean that the compiler will declare

B& B::operator =(const B&)

implicitly. It will hide the operator inherited from `A`. The line

b = c;

does not compile, because, the only candidate here is the above implicitly declared `B::operator =` (the compiler told you about that already); all other candidates are hidden. And since `c` is not convertible to `B&`, the above assignment does not compile.

If you want your code to compile, you can use using-declaration to unhide the inherited `A::operator =` by adding

using A::operator =;

to the definition of class `B`. The code will now compile, although it won't be a good style. You have to keep in mind that in this case the `b = c` assignment will invoke `A::operator =`, which assigns only the `A` portions of the objects involved. (But apparently that is your intent.)

Alternatively, in cases like this you can always work around name hiding by using a qualified version of the name

b.A::operator =(c);

Problem

I'm having trouble with the inheritance of operator=. Why doesn't this code work, and what is the best way to fix it? ``` #include <iostream> class A { public: A & operator=(const A & a) { x = a.x; return *this; } bool operator==(const A & a) { return x == a.x; } virtual int get() = 0; // Abstract protected: int x; }; class B : public A { public: B(int x) { this->x = x; } int get() { return x; } }; class C : public A { public: C(int x) { this->x = x; } int get() { return x; } }; int main() { B b(3); C c(7); printf("B: %d C: %d B==C: %d\n", b.get(), c.get(), b==c); b = c; // compile error // error: no match for 'operator= in 'b = c' // note: candidates are B& B::operator=(const B&) printf("B: %d C: %d B==C: %d\n", b.get(), c.get(), b==c); return 0; } ```

Original source