如何将派生类型的对象放在一个基本类型的向量中?

问题描述 投票:-2回答:3

我刚开始这个项目,我一直坚持如何实现我的ChessBoard类。我想要的是我的std::vector<std::vector<ChessPiece*>>存储从它派生的类型的对象(特定的棋子)。 查看ChessBoard类中std::vector<std::vector<ChessPiece*>> board的赋值。

#include <iostream>
#include <string>
#include <vector>

enum class COLOR
{
    BLACK,
    WHITE,
    NOTHING
};

class ChessPiece
{
protected:
    COLOR color;

public:
    ChessPiece() = default;
    ChessPiece(COLOR c) : color{ c } {}
    COLOR get_color() const { return color; }

    friend std::ostream& operator<<(std::ostream& out, const ChessPiece piece)
    {
        if (piece.color == COLOR::BLACK)
            return out << '-';
        if (piece.color == COLOR::WHITE)
            return out << '+';
    }
};

class King : public ChessPiece
{
private:
    bool moved;

public:
    King() = default;
    King(COLOR c) { color = c; }
    void set_moved(bool b) { moved = b; }
    bool has_moved() { return moved; }
};

class Queen : public ChessPiece
{
private:


public:
    Queen() = default;
    Queen(COLOR c) { color = c; }
};

class Bishop : public ChessPiece
{
private:


public:
    Bishop() = default;
    Bishop(COLOR c) { color = c; }
};

class Knight : public ChessPiece
{
private:


public:
    Knight() = default;
    Knight(COLOR c) { color = c; }
};

class Rook : public ChessPiece
{
private:
    bool moved;

public:
    Rook() = default;
    Rook(COLOR c) { color = c; }
    void set_moved(bool b) { moved = b; }
    bool has_moved() { return moved; }
};

class Pawn : public ChessPiece
{
private:


public:
    Pawn() = default;
    Pawn(COLOR c) { color = c; }
};

class Board
{
private:
    std::vector<std::vector<ChessPiece*>> board[8][8];

    Pawn white_pawn1(COLOR::WHITE), white_pawn2, white_pawn3, white_pawn4, white_pawn5, white_pawn6, white_pawn7, white_pawn8;
    Rook white_rook1, white_rook2;
    Knight white_knight1, white_knight2;
    Bishop white_bishop1, white_bishop2;
    Queen white_queen;
    King white_king;

    Pawn black_pawn1, black_pawn2, black_pawn3, black_pawn4, black_pawn5, black_pawn6, black_pawn7, black_pawn8;
    Rook black_rook1, black_rook2;
    Knight black_knight1, black_knight2;
    Bishop black_bishop1, black_bishop2;
    Queen black_queen;
    King black_king;

public:
    Board(std::string color)
    {
        if (color == "white")
        {
            **board =
            {
                { &black_rook1, &black_knight1, &black_bishop1, &black_queen, &black_king, &black_bishop2, &black_knight2, &black_rook2 },
                { &black_pawn1, &black_pawn2, &black_pawn3, &black_pawn4, &black_pawn5, &black_pawn6, &black_pawn7, &black_pawn8 },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { &white_pawn1, &white_pawn2, &white_pawn3, &white_pawn4, &white_pawn5, &white_pawn6, &white_pawn7, &white_pawn8 },
                { &white_rook1, &white_knight1, &white_bishop1, &white_queen, &white_king, &white_bishop2, &white_knight2, &white_rook2 }
            };
        }
        if (color == "black")
        {
            **board =
            {
                { &white_rook1, &white_knight1, &white_bishop1, &white_queen, &white_king, &white_bishop2, &white_knight2, &white_rook2 },
                { &white_pawn1, &white_pawn2, &white_pawn3, &white_pawn4, &white_pawn5, &white_pawn6, &white_pawn7, &white_pawn8 },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { &black_pawn1, &black_pawn2, &black_pawn3, &black_pawn4, &black_pawn5, &black_pawn6, &black_pawn7, &black_pawn8 },
                { &black_rook1, &black_knight1, &black_bishop1, &black_queen, &black_king, &black_bishop2, &black_knight2, &black_rook2 }
            };
        }
    }

    void print_board()
    {
        std::cout << "\ta\tb\tc\td\te\tf\tg\th\n1\t";
        for (int i = 0; i != 8; ++i)
        {
            for (int j = 0; j != 8; ++j)
            {
                if (board[i][j] == nullptr)
                    std::cout << '#' << std::endl;
                std::cout << board[i][j] << '\t';
            }
            std::cout << std::endl;
            if (i != 7)
                std::cout << i + 2 << '\t';
        }
    }

    ~Board() = default;
};

class Game
{
private:
    bool won;
    bool lost;

public:
    bool is_over();
    void update(std::string);
};

int main()
{
    std::cout << "white or black:\n";
    std::string color;
    std::cin >> color;

    // Start game with your given color on the bottom.
    // TODO throw exception if user enters an invalid color.
    Game game(color);
    std::string move;
    while (!game.is_over())
    {
        std::cin >> move;
        game.update(move);
    }

    system("pause");
    return 0;
}
c++ inheritance vector
3个回答
4
投票
Rook* white_rook1, white_rook2;

不等于

Rook* white_rook1;
Rook* white_rook2;

Rook* white_rook1;
Rook white_rook2;  // not a pointer !!!

(所有其他类似的行相同) 这就是operator =无法匹配的原因。

此外,你不必在这里使用std::vector:你的棋盘在比赛期间不会增长或缩小(除非你有特殊规则:))。请改用std::array

您应该注意,您的代码中没有任何指针被初始化。正如Galik所建议的那样,最好更换对象并将其地址存储在board中。


2
投票

您不创建任何实际对象。到目前为止,你所有的指针都是晃来晃去。除了你的棋盘之外,你还有一整套游戏棋子指针作为成员。

最好使用&(运算符地址)将您的片段成员设为实际对象而不是指针并将其地址放入您的板中。

class Board
{
private:
    std::vector<std::vector<ChessPiece*>> board;

    // make these non-pointers (many of them already were)
    // and give their address to the board
    Pawn white_pawn1, white_pawn2, white_pawn3, white_pawn4, white_pawn5, white_pawn6, white_pawn7, white_pawn8;
    Rook white_rook1, white_rook2;
    Knight white_knight1, white_knight2;
    Bishop white_bishop1, white_bishop2;
    Queen white_queen;
    King white_king;

    Pawn black_pawn1, black_pawn2, black_pawn3, black_pawn4, black_pawn5, black_pawn6, black_pawn7, black_pawn8;
    Rook black_rook1, black_rook2;
    Knight black_knight1, black_knight2;
    Bishop black_bishop1, black_bishop2;
    Queen black_queen;
    King black_king;

public:
    Board(std::string color)
    {
        if (color == "white")
        {
            board =
            { // NOTE the use of & to take their address aand obtain a pointer
                { &black_rook1, &black_knight1, &black_bishop1, &black_queen, &black_king, &black_bishop2, &black_knight2, &black_rook2 },
                { &black_pawn1, &black_pawn2, &black_pawn3, &black_pawn4, &black_pawn5, &black_pawn6, &black_pawn7, &black_pawn8 },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { &white_pawn1, &white_pawn2, &white_pawn3, &white_pawn4, &white_pawn5, &white_pawn6, &white_pawn7, &white_pawn8 },
                { &white_rook1, &white_knight1, &white_bishop1, &white_queen, &white_king, &white_bishop2, &white_knight2, &white_rook2 }
            };
        }

通过制作适当的物品,它们可以保持个别状态,您不必担心创建和销毁它们 - 只需将它们移动到板上(或上下)。

我也会考虑使用std::array<std::array<ChessPiece*>, 8>, 8>而不是矢量。但这将使你的Board对象更大。


0
投票

我认为你没有通过使用矢量得到任何东西,你可以使用2D数组。喜欢:

#include <iostream>
#include <string>
#include <vector>

class EmptySquare : public ChessPiece
{
private:


public:

};

class King : public ChessPiece
{
private:


public:

};

class Queen : public ChessPiece
{
private:


public:

};

class Bishop : public ChessPiece
{
private:


public:

};

class Knight : public ChessPiece
{
private:


public:

};

class Rook : public ChessPiece
{
private:


public:

};

class Pawn : public ChessPiece
{
private:


public:

};

enum class COLOR
{
    BLACK,
    WHITE,
    NOTHING
};

class ChessPiece
{
private:
    COLOR color;

public:
    COLOR get_color();
};

class Board
{
private:
    ChessPiece* board[8][8];

    Pawn white_pawn1(COLOR(WHITE)), white_pawn2, white_pawn3, white_pawn4, white_pawn5, white_pawn6, white_pawn7, white_pawn8;
    Rook white_rook1, white_rook2;
    Knight white_knight1, white_knight2;
    Bishop white_bishop1, white_bishop2;
    Queen white_queen;
    King white_king;

    Pawn black_pawn1, black_pawn2, black_pawn3, black_pawn4, black_pawn5, black_pawn6, black_pawn7, black_pawn8;
    Rook black_rook1, black_rook2;
    Knight black_knight1, black_knight2;
    Bishop black_bishop1, black_bishop2;
    Queen black_queen;
    King black_king;

public:
    Board(std::string color)
    {
        if (color == "white")
        {
            ChessPiece* l_board[8][8] =
            {
                { &black_rook1, &black_knight1, &black_bishop1, &black_queen, &black_king, &black_bishop2, &black_knight2, &black_rook2 },
                { &black_pawn1, &black_pawn2, &black_pawn3, &black_pawn4, &black_pawn5, &black_pawn6, &black_pawn7, &black_pawn8 },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { &white_pawn1, &white_pawn2, &white_pawn3, &white_pawn4, &white_pawn5, &white_pawn6, &white_pawn7, &white_pawn8 },
                { &white_rook1, &white_knight1, &white_bishop1, &white_queen, &white_king, &white_bishop2, &white_knight2, &white_rook2 }
            };
            memcpy(board, l_board, sizeof(ChessPiece*) *8 *8);
        }
        if (color == "black")
        {
            ChessPiece* l_board[8][8] =
            {
                { &white_rook1, &white_knight1, &white_bishop1, &white_queen, &white_king, &white_bishop2, &white_knight2, &white_rook2 },
                { &white_pawn1, &white_pawn2, &white_pawn3, &white_pawn4, &white_pawn5, &white_pawn6, &white_pawn7, &white_pawn8 },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr },
                { &black_pawn1, &black_pawn2, &black_pawn3, &black_pawn4, &black_pawn5, &black_pawn6, &black_pawn7, &black_pawn8 },
                { &black_rook1, &black_knight1, &black_bishop1, &black_queen, &black_king, &black_bishop2, &black_knight2, &black_rook2 }
            };
            memcpy(board, l_board, sizeof(ChessPiece*) *8 *8);
        }
    }
    void print_board();

    ~Board();
};

class Game
{
private:
    bool won;
    bool lost;


public:
    bool is_over();
    void update(std::string);
};

int main()
{
    std::cout << "white or black:\n";
    std::string color;
    std::cin >> color;

    // Start game with your given color on the bottom.
    // TODO throw exception if user enters an invalid color.
    Game game(color);
    std::string move;
    while (!game.is_over())
    {
        std::cin >> move;
        game.update(move);
    }

    system("pause");
    return 0;
}
© www.soinside.com 2019 - 2024. All rights reserved.