I'm a bit confused about a "multiple inheritance problem". Consider the following hunk of code:
#include <iostream>
struct iface
{
virtual void foo () = 0;
virtual ~iface () {}
};
struct wrapped
{
virtual void foo ()
{
std::cerr << "wrapped\n";
}
};
struct impl : public wrapped, public iface
{
};
iface* factory ()
{
return new impl;
}
int main ()
{
iface *object = factory ();
object->foo();
delete object;
return 0;
}
This is abstracted out of some code that's using the pimpl idiom. The idea is that wrapped
is some complicated class with all sorts of other bells and whistles. iface
just makes a particular facet of wrapped
visible and the factory()
function builds an impl
class that implements iface
by using wrapped
. In my real code, the wrapped
class comes from a library with an enormous tree of headers, so I define impl
in a separate compilation unit to avoid the rest of my application having to pull them in.
Anyway, what I pasted does not compile, and gives the following error:
$ g++ -o test test.cc
test.cc: In function ‘iface* factory()’:
test.cc:23:16: error: cannot allocate an object of abstract type ‘impl’
return new impl;
^
test.cc:17:8: note: because the following virtual functions are pure within ‘impl’:
struct impl : public wrapped, public iface
^
test.cc:5:18: note: virtual void iface::foo()
virtual void foo () = 0;
^
Obviously, I can avoid the error by writing a concrete implementation of foo
in impl
that forwards to wrapped::foo()
, but I don't understand why the compiler doesn't pick up the implementation from the wrapped
class.
I assume that somehow the "foo" from iface
and the "foo" from wrapped
end up being different when doing name resolution (is that the right word) for impl
, but I don't really understand why.
Can someone explain what's going on?
If any virtual function of a class is a pure virtual then the class is absrtract. Class impl has two member functions with the same name
iface::foo
and
wrapped::foo
The first member function of class impl is pure virtual, so the class is abstract. The compiler may not create an object of an abstract class.