我正在制作一个程序,允许我与电脑玩嘀嗒声。我创建了一个包含3个3个字符阵列的数组来创建网格。
char grid[3][3] = { {' ',' ',' '},
{' ',' ',' '},
{' ',' ',' '}};
我使用以下格式输入:
cout << "\n";
cout << " | | \n";
cout << " 7 | 8 | 9 \n";
cout << " _____|_____|_____ \n";
cout << " | | \n";
cout << " 4 | 5 | 6 \n";
cout << " _____|_____|_____ \n";
cout << " | | \n";
cout << " 1 | 2 | 3 \n";
cout << " | | \n";
cout << "\n";
当用户输入9时,我使用此输入格式[3] [ - 1](在这种情况下输入为9):
grid[input/3][input%3-1] = userMark;
并将用户的标记放在那里,但那个空间是网格[2] [2],而不是网格[3] [ - 1]。有人可以解释为什么我不能发现任何错误,甚至还会播放这样做之后的游戏。感谢所有帮助,谢谢!
这是我的整个计划:
#include <iostream.h.>
#include <stdlib.h>
#include <time.h>
#include <windows.h>
char grid[3][3] = { {' ',' ',' '},
{' ',' ',' '},
{' ',' ',' '}};
char userMark = ' ';
char comMark = ' ';
int difficulty = 0;
showExample();
showGrid();
userMove();
comMove();
reset();
check();
main()
{
//Asking if the user wants to be Xs or Os
while(userMark != 'X' && userMark != 'O')
{
cout << "\n Would you like to be Xs or Os? (enter \'X\' or \'O\')\n\n";
cout << " Mark: ";
cin >> userMark;
}
if(userMark == 'X')
{
comMark = 'O';
}
else
{
comMark = 'X';
}
system( "cls");
//Asking the uswer for the difficulty
while(difficulty <1 || difficulty > 3)
{
cout << " Choose the difficulty level!\n\n";
cout << " 1) The computer is dumb\n";
cout << " 2) You may win\n";
cout << " 3) You will never win\n\n";
cout << " level: ";
cin >> difficulty;
}
//Looping through the game until the use wins or loses
while (check() == 0)
{
system("cls");
if (userMark == 'X')
{
userMove();
if (check() != 0)
{
break;
}
comMove();
}
else
{
comMove();
if (check() != 0)
{
break;
}
userMove();
}
}
//Telling whether the user won or lost after showing the grid
showGrid();
if(check() == 1)
{
cout << " You win!\n\n\n";
}
else if (check() == 2)
{
cout << " You lose!\n\n\n";
}
return 0;
}
以下是我的功能:
showExample()
{
/*
* Shows the numeric values for the places using cout
*/
cout << "\n";
cout << " | | \n";
cout << " 7 | 8 | 9 \n";
cout << " _____|_____|_____ \n";
cout << " | | \n";
cout << " 4 | 5 | 6 \n";
cout << " _____|_____|_____ \n";
cout << " | | \n";
cout << " 1 | 2 | 3 \n";
cout << " | | \n";
cout << "\n";
return 0;
}
/******************************************************************/
showGrid()
{
/*
* Shows the grid with all of the user's moves
*/
cout << "\n";
cout << " | | \n ";
cout << " " << grid[2][0] << " | " << grid[2][1] << " | " << grid[2][2] << endl;
cout << " _____|_____|_____ \n";
cout << " | | \n ";
cout << " " << grid[1][0] << " | " << grid[1][1] << " | " << grid[1][2] << endl;
cout << " _____|_____|_____ \n";
cout << " | | \n ";
cout << " " << grid[0][0] << " | " << grid[0][1] << " | " << grid[0][2] << endl;
cout << " | | \n";
cout << "\n";
return 0;
}
/******************************************************************/
userMove()
{
/*
* Asks for input from the user and puts that in grid if there is no something already there
*/
int input = 0;
while(input<1 || input>9 || grid[input/3][input%3-1] != ' ')
{
showExample();
showGrid();
cout << " Please enter the place you would like to mark: ";
cin >> input;
system("cls");
}
grid[input/3][input%3-1] = userMark;
cout << "grid: " << grid[3][3] << endl;
return 0;
}
/******************************************************************/
comMove()
{
/*
* Making the computer's move based on the difficulty level
*/
int move = 0;
if(difficulty == 1)
{
do
{
Sleep(700);
srand((unsigned int)time(NULL));
move = rand() % 9 + 1;
} while(grid[move/3][move%3-1] != ' ');
}
else if (difficulty == 2)
{
}
else
{
}
grid[move/3][move%3-1] = comMark;
return 0;
}
/******************************************************************/
reset()
{
/*
* Resets the grid to the correct places using a for loop nested in a another for loop
*/
for(int place=0, row=0; row<3; row++)
{
for(int column=0; column<3; column++, place++)
{
grid[row][column] = ' ';
}
}
return 0;
}
/******************************************************************/
check()
{
//Checking for 3 in a row
for(int position=0; position<3; position++)
{
if(grid[position][0] + grid[position][1] + grid[position][2] == userMark*3 || grid[0][position] + grid[1][position] + grid[2][position] == userMark*3)
{
return 1;
}
else if(grid[position][0] + grid[position][1] + grid[position][2] == comMark*3 || grid[0][position] + grid[1][position] + grid[2][position] == comMark*3)
{
return 2;
}
}
//Checking diagonals for 3 in a row
if(grid[0][0] + grid[1][1] + grid[2][2] == userMark*3 || grid[0][2] + grid[1][1] + grid[2][0] == userMark*3)
{
return 1;
}
else if(grid[0][0] + grid[1][1] + grid[2][2] == comMark*3 || grid[0][2] + grid[1][1] + grid[2][0] == comMark*3)
{
return 2;
}
return 0;
}
答案 0 :(得分:1)
传统的C风格数组没有范围检查。它们只是根据索引计算偏移量,将偏移量添加到数组的开头,然后写入该地址。
在你的情况下[3] [ - 1]将给出3 * 3 - 1 = 8
的偏移量如果你看[2] [2]它将给出2 * 3 + 2 = 8
的偏移量因此,当您(错误地)访问[3] [ - 1]时,它恰好与[2] [ - 2]相同,因为您有一个3乘3的数组。
答案 1 :(得分:0)
访问范围数组是undefined behaviour
。因此意味着您可能不会收到错误。您可能会得到奇怪的结果,如随机结果。因此,您应确保您的代码不会导致超出范围问题的解决方案。
关于-1问题,数组上的运算符[]是一种补充:
a[b]
等于*( (a) + (b) )
因此,a[-1]
等于*((a)+(-1))
。然后,您尝试输入指针的前一个内存块。