Reputation: 10650
I have a tricky little problem I have run into. I believe the problem has to do with the way I am casting things.
So I have a base class called combatEntity
. It has the following function
class combatEntity {
public:
virtual void update();
};
I then have a class mob, which is derived from combatEntity
, overrides the update function:
class mob : public combatEntity {
public:
virtual void update();
}
I then have a class named monster
, which is derived from mob
and also overrides the update function.
class monster: public mob {
public:
virtual void update();
}
I have a combatEntity pointer called i
:
combatEntity* i;
Then I have:
//returns a mob* pointer (needs explicit cast)
monster* newMonster = getMob();
i = newMonster;
The getMob()
function:
mob* getMob() {
mob* newMob = new mob();
//set some data in newMob
return newMob;
}
When I call i->update()
, it calls mob::update()
, because newMonster
is set to "new mob();", since getMob()
returns a new mob pointer. When I call i->update()
, I need it to call monster::update()
, but using breakpoints, I see it is calling mob::update()
and not monster::update()
.
so I need to create a new monster
object, but still have it's base class data filled with the object returned from getMob()
, but have the functions overridden properly. I have also tried dynamic_cast, static_cast and reinterpret_cast, and none seem to work. Or I need to cast my base class to a derived class, while properly overriding functions with the derived class.
Hopefully this makes sence. Any advice would be appreciated.
Upvotes: 0
Views: 7402
Reputation: 13320
take a look to your hierarchy tree, make sure the classes are related how you think.
This code
#include <iostream>
struct combatEntity
{
virtual void Update() { std::cout << "Combat Entity\n"; };
};
struct mob : combatEntity
{
virtual void Update() { std::cout << "Mob\n"; };
};
struct monster : mob
{
virtual void Update() { std::cout << "Monster\n"; };
};
int main(int argc, char **argv)
{
combatEntity *ce = new monster;
ce->Update();
delete ce;
return 0;
}
creates this output:
Monster
Source: http://ideone.com/k6LAB
Upvotes: 2
Reputation: 12496
Well, since you're using virtual, "update" will always call the correct function, no matter what you declare the pointer to be. That's just how "virtual" works.
If you want your pointers to determine what gets called, rather than the object themselves, make the stuff non-virtual. In this case, the pointer-type will determine which "update" is getting called.
If you want both, you can still call something like monster::update() instead of just update. However, unless you're doing this from inside a derived class' update function (to invoke the superclass implementation), trying to get past the inheritance hierarchy may be a sign of bad design.
Upvotes: 0
Reputation: 45414
Your line
monster* newMonster = getMob();
should not compile. I get
error: invalid conversion from ‘mob*’ to ‘monster*’ [-fpermissive]
(also your line i = monster;
should presumably read i = newMonster;
). This explains it all, I think (see also comment from Luchian).
Upvotes: 0