简体   繁体   中英

How to dereference derived class objects stored in a vector of smart pointers?

I'm building a chess game. I have a base class gamePiece and a derived class called rook.

I originally wanted to put all different types of pieces inside one vector and traverse it with an iterator. However, I previously discovered that I could not insert a rook object inside a vector for gamePiece objects.

Many people recommended I instead use pointers to accomplish what I needed--smart pointers were suggested, specifically unique_ptr and shared_ptr. To see the discussion in my previous question, see the link below:

How to reference derived objects in a vector of pointers to base class objects?

The specific technique suggested for unique_ptr is here:

vector<std::unique_ptr<gamePiece>> vectorOfPointersToGamePieces;
std::unique_ptr<gamePiece> rk( new rook(1, "Rook", 'A', 1, "White", "Up") );
vectorOfPointersToGamePieces.push_back(std::move(rk));

The specific technique for shared_ptr is here:

vector<std::shared_ptr<gamePiece>> vectorOfPointersToGamePieces;
vectorOfPointersToGamePieces.push_back(std::make_shared<rook>(1, "Rook", 'A', 1, "White", "Up") );

However, neither of these techniques seems to be working for me. Actually, I should clarify that a bit more--it partially works. When used with "rook" (derived) objects the display function reports that my strings are empty and the variables look unitialized, even though everything in the constructors appears to be working fine.

Yet when these techniques are used with "gamePiece" (base) objects, the display function displays everything perfectly... So there must be a reason why this is working perfectly with base class objects, but not with derived objects.

Is there some kind of step I'm missing (like do I need to cast a "rook" into a "gamePiece" before putting it in the vector...)? I also read on another post somewhere that certain types of smart pointers can't go inside STL containers. Is this one of those cases? Or maybe it doesn't recognize that rook is a derived object of a gamePiece. That class is below.

class rook: public gamePiece
{

public:
rook(int player, string type, char file, int rank, string color, string facing)
{
    gamePiece(player, type, file, rank, color, facing);
}

};
rook(int player, string type, char file, int rank, string color, string facing)
 : gamePiece(player, type, file, rank, color, facing) {}

.. is the correct way to call a parent constructor from a derived class. What you are doing internally is not initializing the object itself, but calling the constructor directly. I'm surprised your compiler lets you do that. The rook object is likely calling the default constructor of gamePiece (I assume you have something like gamePiece() {} defined in your gamepiece class).

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM