首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >C++成员函数清空矩阵

C++成员函数清空矩阵
EN

Stack Overflow用户
提问于 2011-12-20 19:35:49
回答 4查看 305关注 0票数 0

我在很多项目中遇到过类似的问题,这些项目都涉及到包含数组的类。我有一个类,它应该处理一个表示TicTacToe游戏的二维矩阵。类中有一个用于当前游戏状态的枚举和一个具有枚举返回类型的成员函数。我似乎不明白为什么我可以在矩阵中创建类集值,并且只要我使用枚举返回类型调用成员函数,整个数组就会重新初始化为0。我认为这与构造函数被再次调用或类似的东西有关,但在过去几个小时的搜索中,我没有找到任何东西。任何帮助都将不胜感激。

下面是我的头文件,其中包含类信息:

代码语言:javascript
复制
#ifndef TTT_H
#define TTT_H

#include <cstdlib>
#include <iostream>

using namespace std;

class TicTacToe
{
private:
    enum Status{WinX, WinO, Continue, Draw};
    int **board;

public:
    TicTacToe();
    ~TicTacToe();
    void PrintBoard();
    bool ValidMove(int, int);
    bool PlayerMove(int, int, int);
    Status GameStatus();    //this one causes the problem
    void Debug();
};

#endif 

以下是包含成员函数定义的CPP文件的代码:

代码语言:javascript
复制
#include "TicTacToe.h"
#include <iostream>
#include <cstdlib>
#include <iomanip>
#include <cassert>

using namespace std;

TicTacToe::TicTacToe() 
{
    board = new int*[3];
    assert(board != 0);

    for(int i=0;i<3;i++)
    {
        cout << "Constructor Ran again" << endl;    //for testing
        board[i] = new int[3];
        assert(board[i] != 0);
        for(int j=0;j<3;j++)
            board[i][j] = 9;
    }
}

TicTacToe::TicTacToe(TicTacToe &copy)
{
    board = new int*[3];
    assert(board != 0);
}

TicTacToe::~TicTacToe()
{
    if(board)
        delete[] board;
}

void TicTacToe::PrintBoard() 
{
    for(int i=0;i<3;++i)
    {
        for(int j=0;j<3;++j)
        {
            cout << "| ";

            switch(board[i][j]){
            case 0:
                cout << "O ";
                break;
            case 1:
                cout << "X ";
                break;
            case 9:
                cout << "  ";
                break;
            }
        }
        cout << "|" << endl;
        cout << "------------" << endl;
    }
}

bool TicTacToe::ValidMove(int row, int col) 
{
    bool valid = false;
    if(row < 3 && col < 3)
    {
        if(board[row][col] == 9)
            valid = true;
    }
    return valid;
}

bool TicTacToe::PlayerMove(int player, int row, int col) 
{
    bool done = false;

    if(ValidMove(row,col) == true)
    {
        if(player == 1)
            board[row][col] = 1;
        else
            board[row][col] = 0;
        done = true;
    }

    return done;
}

TicTacToe::Status TicTacToe::GameStatus() //This function is the problem
{
    int check, empty = 0;
    bool done = false;

    for(int i=0;i<3;++i)
    {
        for(int j=0;j<3;++j)
        {
            check += board[i][j];
            if(board[i][j] = 9)
                empty++;
        }
        if(check == 0)
            return WinO;
        else if(check == 3)
            return WinX;
        check = 0;
    }

    if(empty == 0)
        return Draw;

    for(int i=0;i<3;++i)
    {
        for(int j=0;j<3;++j)
            check += board[j][i];
        if(check == 0)
            return WinO;
        else if(check == 3)
            return WinX;
        check = 0;
    }

    check = board[0][0] + board[1][1] + board[2][2];
    if(check == 0)
        return WinO;
    else if(check == 3)
        return WinX;
    check = 0;

    check = board[0][2] + board[1][1] + board[2][0];
    if(check == 0)
        return WinO;
    else if(check == 3)
        return WinX;
    check = 0;


    return Continue;
}



void TicTacToe::Debug()
{
    //cout << &board[0][0] << endl;
    for(int i=0;i<3;++i)
    {
        for(int j=0;j<3;++j)
            cout << board[i][j];
        cout << endl;
    }
}

下面是我用来测试的驱动文件:

代码语言:javascript
复制
#include "TicTacToe.h"
#include <iostream>
#include <cassert>

using namespace std;

int main()
{
    int row, col;
    bool valid;
    enum Status{WinX, WinO, Continue, Draw};
    TicTacToe * T;
    T = new TicTacToe;
    assert(T != 0);

    cout << "There are 2 players. P1 is x P2 is o" << endl;

    do
    {
        T->PrintBoard();

        valid = false;
        while(valid == false)
        {
            cout << "\nP1 choose a cell" ;
            cin >> row >> col;

            if(T->ValidMove(row, col) == true)
            {
                T->PlayerMove(1, row, col);
                valid = true;
            }
            else
            {
                cout << "Not a valid choice" << endl;
                valid = false;  
            }

        }

        T->PrintBoard();
        cout << endl;

        T->GameStatus();  //<<<<<this is the pain in my butt

        T->PrintBoard();

        valid = false;
        while(valid == false)
        {
            cout << "\nP2 choose a cell" ;
            cin >> row >> col;

            if(T->ValidMove(row, col) == true)
            {
                T->PlayerMove(2, row, col);
                valid = true;
            }
            else
            {
                cout << "Not a valid choice" << endl;
                valid = false;  
            }
        }   
    }
    while(/*T->GameStatus() == Continue*/ 1==1);
                  //the call to GameStatus was commented out of the
                  //while statement for testing


    return 0;

    }

我知道GameStatus函数内部的代码并不美观,但是在处理这些行之前,数组就被搞乱了。

我保留了所有其他函数,只是为了表明它们工作正常,没有问题。

提前感谢您所能给予的任何帮助。

EN

回答 4

Stack Overflow用户

回答已采纳

发布于 2011-12-20 19:39:42

你的代码中有一个简单的拼写错误..

代码语言:javascript
复制
if(board[i][j] = 9) // will always return true (refp)
  empty++;

其他备注

当更彻底地查看您的代码时,我发现您还有一些其他的遗漏--有意或无意的。我不知道:

没有在TicTacToe::GameStatus

  • You中初始化
  • int check如果没有正确释放分配的内存,则需要释放board中的所有条目,即。delete board[i])

我不喜欢bug,我怎样才能摆脱operator=和operator==的问题呢?

当你想要比较(==)两个变量时,避免输入错误和编写=的一个非常常见的方法是反转操作数(如果其中一个是常量值,比如9

if(9 = board[i][j])不会编译,这样的bug永远不会出现在您的代码中。

我不得不说,我不喜欢这样写我的声明。虽然这是一个很常见的方法,特别是在“初学者”部分。

票数 3
EN

Stack Overflow用户

发布于 2011-12-20 19:40:13

未在GameStatus()中初始化check

票数 1
EN

Stack Overflow用户

发布于 2011-12-20 19:43:00

代码语言:javascript
复制
if (board[i][j] = 9)

上面这行代码不是在重置数组内容吗?您可能希望在这里使用==

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8574792

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档