Reputation: 21917
Forgive the obscure title. It's likely a duplicate but I couldn't find the correct phrase.
Consider the following inheritance hierarchy.
class A
{
public:
virtual void Foo(int i) { printf("A::Foo(int i)\n"); }
void Foo(int a, int b) { Foo(a + b); }
};
class B : public A
{
public:
void Foo(int i) override { printf("B::Foo(int i)\n"); }
};
class C : public B
{
public:
void Bar() { Foo(1, 2); } //error C2660: function does not take two arguments
};
A
has two methods named Foo
with a different number of parameters. Only one of them is virtual.
B
overrides the virtual method.
C
tries to call the non-virtual method and encounters an error.
Calling the method as A::Foo(1, 2)
does work fine.
Question:
Why can't the compiler deduce that the correct method is found on A
?
It seems odd we would have to explicitly add A::
in a call such as:
C c;
c.A::Foo(1, 2);
Upvotes: 2
Views: 95
Reputation: 172874
Because the member function named Foo
is found at the class scope of B
, and then name lookup stops, so the Foo
in class A
is not visible, and won't be considered for overload resolution, even if the version in class A
is more appropriate. It is name hiding.
You can use using
to introduce them into the same scope, and make overload resolution work as you expect. Such as:
class C : public B
{
using A::Foo;
using B::Foo;
public:
void Bar() { Foo(1, 2); }
};
Upvotes: 3