所以我正在开发一个Tic-Tac-Toe游戏,对于我的输入功能,我得到了玩家在二维数组中作为整数存储的移动,输入是使用对一维数组的引用得到的指向2D数组中位置的指针。
然而我的问题是,当我似乎通过使用指针将多维数组的平方值设置为某个东西时,没有任何反应。
这是输入功能:
void Game::input(Board b){
int *spots[9]; // Possible spots for the input
bool validInput = false;
spots[0] = &b.board[2][0];
spots[1] = &b.board[2][1];
spots[2] = &b.board[2][2];
spots[3] = &b.board[1][0];
spots[4] = &b.board[1][1];
spots[5] = &b.board[1][2];
spots[6] = &b.board[0][0];
spots[7] = &b.board[0][1];
spots[8] = &b.board[0][2];
redo:
cout << ">> " << endl;
int input; // Input
cin >> input; // Get the input
validInput = cin;
if(!validInput){
cout << "Numbers only please!" << endl;
cin.clear();
while(cin.get() != '\n');
goto redo;
}
if(input > 9 || input <= 0){
cout << "Invalid move!" << endl;
goto redo;
}
input--; // Subtract 1 for array location
if(*spots[input] != 0){
cout << "Square is already being used!" << endl;
goto redo;
}
*spots[input] = 1;
}
现在,我输入数字7.它应该将b.board [0] [0]设置为1. 但是这似乎不会发生。当我之后运行单元格时,板[0] [0]似乎没有设置为1,并且它不会反映在我的数组中。我在这里弄乱指针吗?
答案 0 :(得分:6)
函数的参数是按值传递的,因此您对其所做的任何更改都无法识别,因为按值传递会创建参数的副本。请考虑通过指针或引用传递。
答案 1 :(得分:3)
您将Board
实例的值传递给input()
而不是指针/引用。您对该Board
实例所做的任何更改都不会反映在传递给Board
的原始input()
实例中。
BTW,paranthesis和loop是你的朋友:
void Game::input(Board &b)
{
int* spots[9]; // Possible spots for the input
bool validInput;
int input;
spots[0] = &(b.board[2][0]);
spots[1] = &(b.board[2][1]);
spots[2] = &(b.board[2][2]);
spots[3] = &(b.board[1][0]);
spots[4] = &(b.board[1][1]);
spots[5] = &(b.board[1][2]);
spots[6] = &(b.board[0][0]);
spots[7] = &(b.board[0][1]);
spots[8] = &(b.board[0][2]);
do
{
std::cout << ">> " << std::endl;
std::cin >> input; // Get the input
validInput = std::cin;
if (!validInput)
{
std::cout << "Numbers only please!" << std::endl;
std::cin.clear();
while (std::cin.get() != '\n');
continue;
}
if ((input > 9) || (input <= 0))
{
std::cout << "Invalid move!" << std::endl;
continue;
}
--input; // Subtract 1 for array location
if (*spots[input] != 0)
{
std::cout << "Square is already being used!" << std::endl;
continue;
}
*spots[input] = 1;
break;
}
while (true);
}
答案 2 :(得分:2)
将方法签名更改为
void Game::input(Board& b)
通过这种方式,您实际上会看到您对其所做的更改。 此时您正在按值调用方法。
答案 3 :(得分:2)
你可以尝试的另一件事是选择这一举动的一点点数学。假设用户输入7. 7/3 = 2,即行。该列为7%3 = 1。所以7指的是board[2][1]
,这是正确的位置。
答案 4 :(得分:0)
您的输入函数声明为:
void Game::input(Board b)
当您从其他功能(例如
)调用此功能时Board tictactoe;
Game g;
g.input(tictactoe);
b
获得tictactoe
的副本。您在input()
功能b
中所做的任何更改都不会反映在tictactoe
中。
您至少有两个解决方案:
1)通过参考传递董事会:
void Game::input(Board& b)
2)或者将指针传递给棋盘:
void Game::input(Board* b)
还有其他解决方案需要重新设计代码。这两个可能是解决当前问题的最简单,最直接的方法。
此外,将索引从一维数组映射到二维数组的方式对我来说有点奇怪。我认为,如果你有
,那么跟踪发生的事情会更容易spots[0] = &(b.board[0][0]);
spots[1] = &(b.board[0][1]);
spots[2] = &(b.board[0][2]);
spots[3] = &(b.board[1][0]);
spots[4] = &(b.board[1][1]);
spots[5] = &(b.board[1][2]);
spots[6] = &(b.board[2][0]);
spots[7] = &(b.board[2][1]);
spots[8] = &(b.board[2][2]);
事实上,正如其他人所说,这是不必要的,因为您可以从输入计算行和col索引。或者,您可以要求用户输入两个数字而不是一个。