On Oct 31, 9:21 am, Erik Wikström <Erik-wikst...@telia.comwrote:
On 2007-10-31 06:49, Just me wrote:
On Wed, 31 Oct 2007 05:11:31 +0000, Tim H wrote:
[...]
If you look closely you will see that getPtr() is declared
virtual in the base class and the correct sublcass::getPtr()
is being called. I verified this by inserting an exit(0) in
subclass::getPtr().
What Tim meant was that you are not allowed to change the
return type of a virtual function. However, returning a type
that is a subtype of the original function's is allowed, but
that does not help you.
What you meant is that returning a pointer or a reference to a
derived type when the function in the base class returns a
pointer or reference to a base is legal. It's called co-variant
return. But of course, the type of the pointer which gets used
at the call site is determined statically. If the static type
is base*, it can only be used to call functions declared in
base. Regardless of what the base* really points to.
Since p is a "base" and getPtr() is not virtual, I would
expect the compiler to generate a call to base::getPtr().
Since base doesn't have an isA() method in this code, I'd
expect it to fail. Does it actually compile, or does your
real code have a base::isA() method?
see above and note that the compiler error was in the
OP...the virtual nature of getPtr() has been verified but
the compiler wont recognize the subclass* return value of
getPtr() to allow access to subclass::isA().
What I'm seeing is weird because the epxression p->getPtr()
should return a subclass* and that return type should be
compatible with subclass::isA().
No, the pointer p is of of type base*, that means that the
function called is base's getPtr() (but the code that is
executed is one in subclass)
Only if the function is virtual. Basically, the entire call
sequence is first resolved (overloading, etc.) statically.
Then, if and only if the chosen function is declared virtually,
the compiler will invoke the function of the most derived class.
But before any such considerations, the compiler must see a
declaration of the function. Using purely static analysis.
FWIW, this is a standard behavior of a statically typed
language. It's not specific to C++: Java, C# and I believe
Ada95 and Eiffel all have the same behavior. If you want
something different, you need a fully dynamically typed
language, like Lisp or Smalltalk. Which has other
disadvantages: whatever language you choose represents a
compromise between safety and flexibility (with C++ leaning
very, very strongly to the side of safety).
which means that the type of the pointer that is returned from
getPtr() have the type declared in base's getPtr(), namely
base*.
With a pointer to base you can only call base's functions.
Though if they are virtual and the actual type of the object
pointed to is a derived type then the implementation in the
derived type will be used. But it is still the base's
function that was called.
I know what you're trying to say, but that sounds a bit
confusing, since of course, you don't actually call the function
in base---if it is pure virtual, there is no function to call.
I prefer to explain it in terms of compile time "resolution"
(given that we already have to term "overload resolution"). The
compiler must first choose which function to call, statically;
how can it know if the function is virtual until it has choosen
it?
The actual "resolution" is a fairly complex process, involving
name lookup, including ADL, then type deduction on template
parameters, and finally overload resolution. Having "resolved"
the function, the compiler then does things like access checks
(private, etc.), and only after all this does it consider
whether the function is virtual or not, and either call the
function in the statically declared type or the one in the
dynamic type.
What you can do is make isA() a virtual function in base, and
use the value returned to dynamic_cast() the pointer to the
correct subtype.
There are a number of possible solutions, but since we don't
really know the problem...
--
James Kanze (GABI Software) email:ja*********@gmail.com
Conseils en informatique orientée objet/
Beratung in objektorientierter Datenverarbeitung
9 place Sémard, 78210 St.-Cyr-l'École, France, +33 (0)1 30 23 00 34