编写一个小程序,实现五子棋游戏功能。
相关知识
为了完成本关任务,你需要掌握:1.如何定义一个二维数组,2.如何通过下标访问数组元素 3. 注意要把格局检测设计为一个函数。
棋盘样式
棋盘的样式如下:
由 A-O 作为行坐标,1-15作为列坐标,对棋盘的各个点位进行标识。如上图中,棋子O(大写字母O)的坐标为H8,棋子X的坐标为G7,每一次通过输入棋子坐标完成落子。本测试规定一盘的开始格局是 ‘O’ 先落子在H8, 随后由等待用户输入‘X’的坐标,如输入 G7 后回车,棋子X将落在G7位置,如此交替落子。
赢棋规则
率先出现5个及以上棋子连成一条直线的一方获胜。
#include <stdio.h>
#include <string.h>
#define ROW 15
#define COL 15
#define NUM 5
char board[ROW][COL]; // 棋盘
char current_player; // 当前玩家
// 初始化棋盘
void init_board() {
memset(board, ' ', sizeof(board)); // 将棋盘全部赋值为空格
board[ROW / 2][COL / 2] = 'O'; // 初始时白子先落子
current_player = 'X'; // 初始时黑子先落子
}
// 输入落子坐标
void input_pos(int *row, int *col) {
char c1, c2;
printf("%c's turn, please input a position: ", current_player);
scanf(" %c%c", &c1, &c2); // 输入棋子坐标
*row = c1 - 'A'; // 行坐标
*col = c2 - '1'; // 列坐标
}
// 检查输赢
int check_win(int row, int col) {
int i, j;
char c = board[row][col]; // 当前棋子
// 检查横向连续的棋子数
i = row;
j = col;
while (j > 0 && board[i][j - 1] == c) j--; // 向左搜索
int count = 0;
while (j < COL && board[i][j] == c) {
j++;
count++;
}
if (count >= NUM) return 1; // 如果横向连续的棋子数大于等于 NUM,则当前玩家获胜
// 检查纵向连续的棋子数
i = row;
j = col;
while (i > 0 && board[i - 1][j] == c) i--; // 向上搜索
count = 0;
while (i < ROW && board[i][j] == c) {
i++;
count++;
}
if (count >= NUM) return 1; // 如果纵向连续的棋子数大于等于 NUM,则当前玩家获胜
// 检查左上到右下的对角线上连续的棋子数
i = row;
j = col;
while (i > 0 && j > 0 && board[i - 1][j - 1] == c) {
i--;
j--;
}
count = 0;
while (i < ROW && j < COL && board[i][j] == c) {
i++;
j++;
count++;
}
if (count >= NUM) return 1; // 如果左上到右下的对角线上连续的棋子数大于等于 NUM,则当前玩家获胜
// 检查右上到左下的对角线上连续的棋子数
i = row;
j = col;
while (i > 0 && j < COL && board[i - 1][j + 1] == c) {
i--;
j++;
}
count = 0;
while (i < ROW && j >= 0 && board[i][j] == c) {
i++;
j--;
count++;
}
if (count >= NUM) return 1; // 如果右上到左下的对角线上连续的棋子数大于等于 NUM,则当前玩家获胜
return 0; // 如果以上四种情况都不满足,则没有玩家获胜
}
// 输出棋盘格局
void print_board() {
int i, j;
printf(" ");
for (i = 0; i < COL; i++) {
printf("%c ", '1' + i); // 输出列坐标
}
printf("\n");
for (i = 0; i < ROW; i++) {
printf("%c ", 'A' + i); // 输出行坐标
for (j = 0; j < COL; j++) {
printf("%c ", board[i][j]); // 输出棋子
}
printf("\n");
}
}
int main() {
int row, col;
init_board(); // 初始化棋盘
while (1) {
print_board(); // 输出棋盘格局
input_pos(&row, &col); // 输入落子坐标
board[row][col] = current_player; // 落子
if (check_win(row, col)) { // 检查输赢
printf("%c wins!\n", current_player);
break;
}
// 交换玩家
if (current_player == 'X') {
current_player = 'O';
} else {
current_player = 'X';
}
}
return 0;
}
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include <time.h>
using namespace std;
const int N=15; //15*15的棋盘
const char ChessBoardflag = ' '; //棋盘标志
const char flag1='o'; //玩家1或电脑的棋子标志
const char flag2='X'; //玩家2的棋子标志
typedef struct Coordinate //坐标类
{
int x; //代表行
int y; //代表列
}Coordinate;
class GoBang //五子棋类
{
public:
GoBang() //初始化
{
InitChessBoard();
}
void Play() //下棋
{
Coordinate Pos1; // 玩家1或电脑
Coordinate Pos2; //玩家2
int n = 0;
while (1)
{
int mode = ChoiceMode();
while (1)
{
if (mode == 1) //电脑vs玩家
{
ComputerChess(Pos1,flag1); // 电脑下棋
if (GetVictory(Pos1, 0, flag1) == 1) //0表示电脑,真表示获胜
break;
PlayChess(Pos2, 2, flag2); //玩家2下棋
if (GetVictory(Pos2, 2, flag2)) //2表示玩家2
break;
}
else //玩家1vs玩家2
{
PlayChess(Pos1, 1, flag1); // 玩家1下棋
if (GetVictory(Pos1, 1, flag1)) //1表示玩家1
break;
PlayChess(Pos2, 2, flag2); //玩家2下棋
if (GetVictory(Pos2, 2, flag2)) //2表示玩家2
break;
}
}
cout << "***再来一局***" << endl;
cout << "y or n :";
char c = 'y';
cin >> c;
if (c == 'n')
break;
}
}
protected:
int ChoiceMode() //选择模式
{
int i = 0;
system("cls"); //系统调用,清屏
InitChessBoard(); //重新初始化棋盘
cout << "***0、退出 1、电脑vs玩家 2、玩家vs玩家***" << endl;
while (1)
{
cout << "请选择:";
cin >> i;
if (i == 0) //选择0退出
exit(1);
if (i == 1 || i == 2)
return i;
cout << "输入不合法" << endl;
}
}
void InitChessBoard() //初始化棋盘
{
for (int i = 0; i < N + 1; ++i)
{
for (int j = 0; j < N + 1; ++j)
{
_ChessBoard[i][j] = ChessBoardflag;
}
}
}
void PrintChessBoard() //打印棋盘,这个函数可以自己调整
{
system("cls"); //系统调用,清空屏幕
for (int i = 0; i < N+1; ++i)
{
for (int j = 0; j < N+1; ++j)
{
if (i == 0) //打印列数字
{
if (j!=0)
printf("%d ", j);
else
printf(" ");
}
else if (j == 0) //打印行数字
printf("%2d ", i);
else
{
if (i < N+1)
{
printf("%c |",_ChessBoard[i][j]);
}
}
}
cout << endl;
cout << " ";
for (int m = 0; m < N; m++)
{
printf("--|");
}
cout << endl;
}
}
void PlayChess(Coordinate& pos, int player, int flag) //玩家下棋
{
PrintChessBoard(); //打印棋盘
while (1)
{
printf("玩家%d输入坐标:", player);
cin >> pos.x >> pos.y;
if (JudgeValue(pos) == 1) //坐标合法
break;
cout << "坐标不合法,重新输入" << endl;
}
_ChessBoard[pos.x][pos.y] = flag;
}
void ComputerChess(Coordinate& pos, char flag) //电脑下棋
{
PrintChessBoard(); //打印棋盘
int x = 0;
int y = 0;
while (1)
{
x = (rand() % N) + 1; //产生1~N的随机数
srand((unsigned int) time(NULL));
y = (rand() % N) + 1; //产生1~N的随机数
srand((unsigned int) time(NULL));
if (_ChessBoard[x][y] == ChessBoardflag) //如果这个位置是空的,也就是没有棋子
break;
}
pos.x = x;
pos.y = y;
_ChessBoard[pos.x][pos.y] = flag;
}
int JudgeValue(const Coordinate& pos) //判断输入坐标是不是合法
{
if (pos.x > 0 && pos.x <= N&&pos.y > 0 && pos.y <= N)
{
if (_ChessBoard[pos.x][pos.y] == ChessBoardflag)
{
return 1; //合法
}
}
return 0; //非法
}
int JudgeVictory(Coordinate pos, char flag) //判断有没有人胜负(底层判断)
{
int begin = 0;
int end = 0;
int begin1 = 0;
int end1 = 0;
//判断行是否满足条件
(pos.y - 4) > 0 ? begin = (pos.y - 4) : begin = 1;
(pos.y + 4) >N ? end = N : end = (pos.y + 4);
for (int i = pos.x, j = begin; j + 4 <= end; j++)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i][j + 1] == flag&&
_ChessBoard[i][j + 2] == flag&&_ChessBoard[i][j + 3] == flag&&
_ChessBoard[i][j + 4] == flag)
return 1;
}
//判断列是否满足条件
(pos.x - 4) > 0 ? begin = (pos.x - 4) : begin = 1;
(pos.x + 4) > N ? end = N : end = (pos.x + 4);
for (int j = pos.y, i = begin; i + 4 <= end; i++)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j] == flag&&
_ChessBoard[i + 2][j] == flag&&_ChessBoard[i + 3][j] == flag&&
_ChessBoard[i + 4][j] == flag)
return 1;
}
int len = 0;
//判断主对角线是否满足条件
pos.x > pos.y ? len = pos.y - 1 : len = pos.x - 1;
if (len > 4)
len = 4;
begin = pos.x - len; //横坐标的起始位置
begin1 = pos.y - len; //纵坐标的起始位置
pos.x > pos.y ? len = (N - pos.x) : len = (N - pos.y);
if (len>4)
len = 4;
end = pos.x + len; //横坐标的结束位置
end1 = pos.y + len; //纵坐标的结束位置
for (int i = begin, j = begin1; (i + 4 <= end) && (j + 4 <= end1); ++i, ++j)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j + 1] == flag&&
_ChessBoard[i + 2][j + 2] == flag&&_ChessBoard[i + 3][j + 3] == flag&&
_ChessBoard[i + 4][j + 4] == flag)
return 1;
}
//判断副对角线是否满足条件
(pos.x - 1) >(N - pos.y) ? len = (N - pos.y) : len = pos.x - 1;
if (len > 4)
len = 4;
begin = pos.x - len; //横坐标的起始位置
begin1 = pos.y + len; //纵坐标的起始位置
(N - pos.x) > (pos.y - 1) ? len = (pos.y - 1) : len = (N - pos.x);
if (len>4)
len = 4;
end = pos.x + len; //横坐标的结束位置
end1 = pos.y - len; //纵坐标的结束位置
for (int i = begin, j = begin1; (i + 4 <= end) && (j - 4 >= end1); ++i, --j)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j - 1] == flag&&
_ChessBoard[i + 2][j - 2] == flag&&_ChessBoard[i + 3][j - 3] == flag&&
_ChessBoard[i + 4][j - 4] == flag)
return 1;
}
for (int i = 1; i < N + 1; ++i) //棋盘有没有下满
{
for (int j =1; j < N + 1; ++j)
{
if (_ChessBoard[i][j] == ChessBoardflag)
return 0; //0表示棋盘没满
}
}
return -1; //和棋
}
bool GetVictory(Coordinate& pos, int player, int flag) //对JudgeVictory的一层封装,得到具体那个玩家获胜
{
int n = JudgeVictory(pos, flag); //判断有没有人获胜
if (n != 0) //有人获胜,0表示没有人获胜
{
PrintChessBoard();
if (n == 1) //有玩家赢棋
{
if (player == 0) //0表示电脑获胜,1表示玩家1,2表示玩家2
printf("***电脑获胜***\n");
else
printf("***恭喜玩家%d获胜***\n", player);
}
else
printf("***双方和棋***\n");
return true; //已经有人获胜
}
return false; //没有人获胜
}
private:
char _ChessBoard[N+1][N+1];
};
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
#include<time.h>
#define ROW 5
#define COL 5
char qi[ROW][COL];
//打印菜单
void print(char qi[ROW][COL])
{
for (int row=0;row<ROW;row++)
{
printf("************************************\n");
printf("| | | | | |\n");
printf("| %c | %c | %c | %c | %c |\n", qi[row][0], qi[row][1], qi[row][2], qi[row][3], qi[row][4]);
printf("| | | | | |\n");
}
printf("************************************\n");
}
//检查是否下满
int is_full(char qi[ROW][COL])
{
for (int row = 0; row < ROW; row++)
{
for (int col = 0; col < COL; col++)
{
if (qi[row][col] == ' ')
{
return 1;
}
}
}
return 0;
}
//检查输赢
char winner(char qi[ROW][COL])
{
int row;
int col;
//遍历每一行,检查是否有相同棋子
for ( row = 0; row < ROW; row++)
{
if (qi[row][0] == qi[row][1] && qi[row][0] == qi[row][2] && qi[row][0] == qi[row][3] && qi[row][0] == qi[row][4] && qi[row][0]!=' ')
{
return qi[row][0];
}
}
//遍历每一列,检查是否有相同棋子
for ( col = 0; col < COL; col++)
{
if (qi[0][col] == qi[1][col] && qi[0][col] == qi[2][col] && qi[0][col] == qi[3][col] && qi[0][col] == qi[4][col] && qi[0][col]!=' ')
{
return qi[0][col];
}
}
//检查对角线是否有相同棋子
if (qi[0][0] == qi[1][1] && qi[0][0]== qi[2][2] && qi[0][0] == qi[3][3] && qi[0][0] == qi[4][4] && qi[0][0]!=' ')
{
return qi[0][0];
}
else if (qi[0][4] == qi[1][3] &&qi[0][4] == qi[2][2] && qi[0][4] == qi[3][1] && qi[0][4] == qi[4][0] && qi[0][4]!=' ')
{
return qi[0][4];
}
//平局
else if (is_full(qi) == 1)
{
return ' ';
}
else
{
return 'p';
}
}
//检查该位置是否有子
int is_exist(char qi[ROW][COL], int row, int col)
{
if (qi[row][col] == ' ')
{
return 1;
}
return 0;
}
//玩家落子
void player_move(char qi[ROW][COL])
{
int row = 0;
int col = 0;
while (1)
{
printf("请输入您想要落子的下标(x y):");
scanf("%d %d", &row, &col);
if (row < 0 || row >= ROW || col < 0 || col >= COL)
{
printf("输入不合法,请重新输入:");
continue;
}
if (is_exist(qi,row,col) == 1)
{
qi[row][col] = 'x';
print(qi);
break;
}
else
{
printf("该位置已经有子,请重新输入:");
continue;
}
}
}
//电脑落子
void computer_move(char qi[ROW][COL])
{
printf("电脑落子\n");
while (1)
{
int row = rand() % ROW;
int col = rand() % COL;
if (is_exist(qi, row, col) == 1)
{
qi[row][col] = 'o';
print(qi);
break;
}
}
}
//打印菜单
void menu()
{
printf("*********************\n");
printf("1、开始游戏\n");
printf("2、退出游戏\n");
printf("*********************\n");
}
//初始化
int Init(char qi[ROW][COL])
{
int choice=0;
menu();//打印菜单
for (int row = 0; row < ROW; row++)//初始化棋盘为空字符
{
for (int col = 0; col < COL; col++)
{
qi[row][col] = ' ';
}
}
scanf("%d", &choice);
if (choice == 1)
{
print(qi);//如果选择开始游戏,打印棋盘
}
else if (choice == 2)
{
printf("Game Over!\n");
}
return choice;
}
int main()
{
//产生随机种子
srand((unsigned)time(0));
while (1)
{
if (Init(qi) == 2 )
{
break;
}
while (1)
{
//玩家落子
player_move(qi);
//检查是否平局
if (winner(qi) == 'p')
{
printf("平局\n");
break;
}
//检查输赢
if (winner(qi) == 'x')
{
printf("游戏结束、玩家胜利!\n");
break;
}
//电脑落子
computer_move(qi);
//检查输赢
if (winner(qi) == 'o')
{
printf("游戏结束、电脑胜利!\n");
break;
}
}
}
system("pause");
return 0;
}
在这里,我将向您展示如何编写一个五子棋游戏的 C 语言小程序。
首先,我们需要定义一个二维数组来表示棋盘,并使用下标访问数组元素来完成棋子的落子操作。这里我们可以使用字母表示行坐标,数字表示列坐标,例如 H8 表示第八行第八列。
我们还需要设计一个函数来检测每一次落子是否已经获胜。这里我们可以使用横向、纵向和对角线方向的检测,如果连成一条直线的棋子数量超过五个,就说明已经获胜。
最后,我们可以使用循环来不断读取用户输入的棋子坐标并进行落子操作,直到游戏结束。
下面是一个示例代码,它实现了五子棋游戏的基本功能:
#include <stdio.h>
#include <string.h>
#define ROW 15
#define COL 15
char board[ROW][COL]; // 定义棋盘
char currPlayer; // 当前玩家
// 初始化棋盘
void initBoard() {
memset(board, ' ', sizeof(board)); // 将棋盘初始化为空白
}
// 输出棋盘
void printBoard() {
printf(" ");
for (int i = 0; i < COL; i++) {
printf("%d ", i + 1); // 输出列坐标
}
printf("\n");
for (int i = 0; i < ROW; i++) {
printf("%c ", 'A' + i); // 输出行坐标
for (int j = 0; j < COL; j++) {
printf("%c ", board[i][j]); // 输出棋子
}
printf("\n");
}
}
// 检测横向是否有五个连续的棋子
int checkHorizontal(int row, int col) {
int count = 1; // 连续棋子数量
int i;
// 向左检测
for (i = col - 1; i >= 0; i--) {
if (board[row][i] != currPlayer) {
break;
}
count++;
}
// 向右检测
for (i = col + 1; i < COL; i++) {
if (board[row][i] != currPlayer) {
break;
}
count++;
}
return count >= 5; // 连续棋子数量大于等于5时返回1,否则返回0
}
// 检测纵向是否有五个连续的棋子
int checkVertical(int row, int col) {
int count = 1; // 连续棋子数量
int i;
// 向上检测
for (i = row - 1; i >= 0; i--) {
if (board[i][col] != currPlayer) {
break;
}
count++;
}
// 向下检测
for (i = row + 1; i < ROW; i++) {
if (board[i][col] != currPlayer) {
break;
}
count++;
}
return count >= 5; // 连续棋子数量大于等于5时返回1,否则返回0
}
// 检测左上至右下的对角线是否有五个连续的棋子
int checkDiagonal1(int row, int col) {
int count = 1; // 连续棋子数量
int i, j;
// 向左上检测
for (i = row - 1, j = col - 1; i >= 0 && j >= 0; i--, j--) {
if (board[i][j] != currPlayer) {
break;
}
count++;
}
// 向右下检测
for (i = row + 1, j = col + 1; i < ROW && j < COL; i++, j++) {
if (board[i][j] != currPlayer) {
break;
}
count++;
}
return count >= 5; // 连续棋子数量大于等于5时返回1,否则返回0
}
// 检测左下至右上的对角线是否有五个连续的棋子
int checkDiagonal2(int row, int col) {
int count = 1; // 连续棋子数量
int i, j;
// 向左下检测
for (i = row + 1, j = col - 1; i < ROW && j >= 0; i++, j--) {
if (board[i][j] != currPlayer) {
break;
}
count++;
}
// 向右上检测
for (i = row - 1, j = col + 1; i >= 0 && j < COL; i--, j++) {
if (board[i][j] != currPlayer) {
break;
}
count++;
}
return count >= 5; // 连续棋子数量大于等于5时返回1,否则返回0
}
// 检测是否有五个连续的棋子
int checkWin(int row, int col) {
return checkHorizontal(row, col) || checkVertical(row, col) || checkDiagonal1(row, col) || checkDiagonal2(row, col);
}
// 游戏主函数
int main() {
initBoard(); // 初始化棋盘
currPlayer = 'O'; // 先落子的玩家为O
int row, col;
while (1) {
printBoard(); // 输出棋盘
printf("请玩家%c输入落子坐标:", currPlayer);
scanf(" %c%d", &row, &col); // 读入玩家输入的坐标
row = row - 'A'; // 将字母坐标转换为数字坐标
col--;
if (board[row][col] != ' ') { // 如果坐标已经有棋子,则提示输入有误
printf("输入有误,请重新输入\n");
continue;
}
board[row][col] = currPlayer; // 在坐标处落子
if (checkWin(row, col)) { // 检测是否胜利
printf("恭喜玩家%c获胜!\n", currPlayer);
break;
}
// 切换玩家
currPlayer = (currPlayer == 'O') ? 'X' : 'O';
}
return 0;
}
上面的代码实现了五子棋游戏的基本功能,在每次落子后检测是否胜利,如果胜利则输出恭喜信息并退出游戏。
希望这份代码能够帮到您。如果您有任何疑问,欢迎随时给我留言。
C语言实现五子棋
借鉴下
https://blog.csdn.net/lyx_04/article/details/125782400
#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include <time.h>
using namespace std;
const int N=15; //15*15的棋盘
const char ChessBoardflag = ' '; //棋盘标志
const char flag1='o'; //玩家1或电脑的棋子标志
const char flag2='X'; //玩家2的棋子标志
typedef struct Coordinate //坐标类
{
int x; //代表行
int y; //代表列
}Coordinate;
class GoBang //五子棋类
{
public:
GoBang() //初始化
{
InitChessBoard();
}
void Play() //下棋
{
Coordinate Pos1; // 玩家1或电脑
Coordinate Pos2; //玩家2
int n = 0;
while (1)
{
int mode = ChoiceMode();
while (1)
{
if (mode == 1) //电脑vs玩家
{
ComputerChess(Pos1,flag1); // 电脑下棋
if (GetVictory(Pos1, 0, flag1) == 1) //0表示电脑,真表示获胜
break;
PlayChess(Pos2, 2, flag2); //玩家2下棋
if (GetVictory(Pos2, 2, flag2)) //2表示玩家2
break;
}
else //玩家1vs玩家2
{
PlayChess(Pos1, 1, flag1); // 玩家1下棋
if (GetVictory(Pos1, 1, flag1)) //1表示玩家1
break;
PlayChess(Pos2, 2, flag2); //玩家2下棋
if (GetVictory(Pos2, 2, flag2)) //2表示玩家2
break;
}
}
cout << "***再来一局***" << endl;
cout << "y or n :";
char c = 'y';
cin >> c;
if (c == 'n')
break;
}
}
protected:
int ChoiceMode() //选择模式
{
int i = 0;
system("cls"); //系统调用,清屏
InitChessBoard(); //重新初始化棋盘
cout << "***0、退出 1、电脑vs玩家 2、玩家vs玩家***" << endl;
while (1)
{
cout << "请选择:";
cin >> i;
if (i == 0) //选择0退出
exit(1);
if (i == 1 || i == 2)
return i;
cout << "输入不合法" << endl;
}
}
void InitChessBoard() //初始化棋盘
{
for (int i = 0; i < N + 1; ++i)
{
for (int j = 0; j < N + 1; ++j)
{
_ChessBoard[i][j] = ChessBoardflag;
}
}
}
void PrintChessBoard() //打印棋盘,这个函数可以自己调整
{
system("cls"); //系统调用,清空屏幕
for (int i = 0; i < N+1; ++i)
{
for (int j = 0; j < N+1; ++j)
{
if (i == 0) //打印列数字
{
if (j!=0)
printf("%d ", j);
else
printf(" ");
}
else if (j == 0) //打印行数字
printf("%2d ", i);
else
{
if (i < N+1)
{
printf("%c |",_ChessBoard[i][j]);
}
}
}
cout << endl;
cout << " ";
for (int m = 0; m < N; m++)
{
printf("--|");
}
cout << endl;
}
}
void PlayChess(Coordinate& pos, int player, int flag) //玩家下棋
{
PrintChessBoard(); //打印棋盘
while (1)
{
printf("玩家%d输入坐标:", player);
cin >> pos.x >> pos.y;
if (JudgeValue(pos) == 1) //坐标合法
break;
cout << "坐标不合法,重新输入" << endl;
}
_ChessBoard[pos.x][pos.y] = flag;
}
void ComputerChess(Coordinate& pos, char flag) //电脑下棋
{
PrintChessBoard(); //打印棋盘
int x = 0;
int y = 0;
while (1)
{
x = (rand() % N) + 1; //产生1~N的随机数
srand((unsigned int) time(NULL));
y = (rand() % N) + 1; //产生1~N的随机数
srand((unsigned int) time(NULL));
if (_ChessBoard[x][y] == ChessBoardflag) //如果这个位置是空的,也就是没有棋子
break;
}
pos.x = x;
pos.y = y;
_ChessBoard[pos.x][pos.y] = flag;
}
int JudgeValue(const Coordinate& pos) //判断输入坐标是不是合法
{
if (pos.x > 0 && pos.x <= N&&pos.y > 0 && pos.y <= N)
{
if (_ChessBoard[pos.x][pos.y] == ChessBoardflag)
{
return 1; //合法
}
}
return 0; //非法
}
int JudgeVictory(Coordinate pos, char flag) //判断有没有人胜负(底层判断)
{
int begin = 0;
int end = 0;
int begin1 = 0;
int end1 = 0;
//判断行是否满足条件
(pos.y - 4) > 0 ? begin = (pos.y - 4) : begin = 1;
(pos.y + 4) >N ? end = N : end = (pos.y + 4);
for (int i = pos.x, j = begin; j + 4 <= end; j++)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i][j + 1] == flag&&
_ChessBoard[i][j + 2] == flag&&_ChessBoard[i][j + 3] == flag&&
_ChessBoard[i][j + 4] == flag)
return 1;
}
//判断列是否满足条件
(pos.x - 4) > 0 ? begin = (pos.x - 4) : begin = 1;
(pos.x + 4) > N ? end = N : end = (pos.x + 4);
for (int j = pos.y, i = begin; i + 4 <= end; i++)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j] == flag&&
_ChessBoard[i + 2][j] == flag&&_ChessBoard[i + 3][j] == flag&&
_ChessBoard[i + 4][j] == flag)
return 1;
}
int len = 0;
//判断主对角线是否满足条件
pos.x > pos.y ? len = pos.y - 1 : len = pos.x - 1;
if (len > 4)
len = 4;
begin = pos.x - len; //横坐标的起始位置
begin1 = pos.y - len; //纵坐标的起始位置
pos.x > pos.y ? len = (N - pos.x) : len = (N - pos.y);
if (len>4)
len = 4;
end = pos.x + len; //横坐标的结束位置
end1 = pos.y + len; //纵坐标的结束位置
for (int i = begin, j = begin1; (i + 4 <= end) && (j + 4 <= end1); ++i, ++j)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j + 1] == flag&&
_ChessBoard[i + 2][j + 2] == flag&&_ChessBoard[i + 3][j + 3] == flag&&
_ChessBoard[i + 4][j + 4] == flag)
return 1;
}
//判断副对角线是否满足条件
(pos.x - 1) >(N - pos.y) ? len = (N - pos.y) : len = pos.x - 1;
if (len > 4)
len = 4;
begin = pos.x - len; //横坐标的起始位置
begin1 = pos.y + len; //纵坐标的起始位置
(N - pos.x) > (pos.y - 1) ? len = (pos.y - 1) : len = (N - pos.x);
if (len>4)
len = 4;
end = pos.x + len; //横坐标的结束位置
end1 = pos.y - len; //纵坐标的结束位置
for (int i = begin, j = begin1; (i + 4 <= end) && (j - 4 >= end1); ++i, --j)
{
if (_ChessBoard[i][j] == flag&&_ChessBoard[i + 1][j - 1] == flag&&
_ChessBoard[i + 2][j - 2] == flag&&_ChessBoard[i + 3][j - 3] == flag&&
_ChessBoard[i + 4][j - 4] == flag)
return 1;
}
for (int i = 1; i < N + 1; ++i) //棋盘有没有下满
{
for (int j =1; j < N + 1; ++j)
{
if (_ChessBoard[i][j] == ChessBoardflag)
return 0; //0表示棋盘没满
}
}
return -1; //和棋
}
bool GetVictory(Coordinate& pos, int player, int flag) //对JudgeVictory的一层封装,得到具体那个玩家获胜
{
int n = JudgeVictory(pos, flag); //判断有没有人获胜
if (n != 0) //有人获胜,0表示没有人获胜
{
PrintChessBoard();
if (n == 1) //有玩家赢棋
{
if (player == 0) //0表示电脑获胜,1表示玩家1,2表示玩家2
printf("***电脑获胜***\n");
else
printf("***恭喜玩家%d获胜***\n", player);
}
else
printf("***双方和棋***\n");
return true; //已经有人获胜
}
return false; //没有人获胜
}
private:
char _ChessBoard[N+1][N+1];
};
#define _CRT_SECURE_NO_WARNINGS 1
#include "game.h"
void menu()
{
printf("*********************************\n");
printf("******** 1. play ********\n");
printf("******** 0. exit ********\n");
printf("*********************************\n");
}
void game()
{
char ret = 0;
//数据的存储需要一个3*3的二维数组
char board[ROW][COL] = { 0 };
init_board(board, ROW, COL);
display_board(board, ROW, COL);
//玩游戏
while (1)
{
player_move(board, ROW, COL);
display_board(board, ROW, COL);
ret = is_win(board, ROW, COL);
if (ret != 'C')
break;
computer_move(board, ROW, COL);
display_board(board, ROW, COL);
ret = is_win(board, ROW, COL);
if (ret != 'C')
break;
}
if (ret == '*')
{
printf("玩家赢\n");
}
else if (ret == '#')
{
printf("电脑赢\n");
}
else if (ret == 'Q')
{
printf("平局\n");
}
display_board(board, ROW, COL);
}
//玩家赢 - '*'
//电脑赢 - '#'
//平局了 - 'Q'
//游戏继续 - 'C'
int main()
{
int input = 0;
srand((unsigned int)time(NULL));
do
{
menu();
printf("请选择:>");
scanf_s("%d", &input);
switch (input)
{
case 1:
game();
break;
case 0:
printf("退出游戏\n");
break;
default:
printf("选择错误,重新选择!\n");
break;
}
} while (input);
return 0;
}
game.h文档内容
#pragma once
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#define ROW 10 //行 ,可以自定义数值的大小
#define COL 10 //列 ,可以自定义数值的大小
//初始化棋盘
void init_board(char board[ROW][COL], int row, int col);
//打印棋盘
void display_board(char board[ROW][COL], int row, int col);
//玩家下棋
void player_move(char board[ROW][COL], int row, int col);
//电脑下棋
void computer_move(char board[ROW][COL], int row, int col);
//判断游戏状态
char is_win(char board[ROW][COL], int row, int col);
game.c文档内容
#define _CRT_SECURE_NO_WARNINGS 1
#include "game.h"
void init_board(char board[ROW][COL], int row, int col)
{
int i = 0;
int j = 0;
for (i = 0; i < row; i++)
{
for (j = 0; j < col; j++)
{
board[i][j] = ' ';
}
}
}
//void display_board(char board[ROW][COL], int row, int col)
//{
// int i = 0;
// for (i = 0; i < row; i++)
// {
// //数据
// printf(" %c | %c | %c \n", board[i][0], board[i][1], board[i][2]);
// //---|---|---
// if(i<row-1)
// printf("---|---|---\n");
// }
//}
void display_board(char board[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
//数据
//printf(" %c | %c | %c \n", board[i][0], board[i][1], board[i][2]);
int j = 0;
for (j = 0; j < col; j++)
{
printf(" %c ", board[i][j]);
if (j < col - 1)
printf("|");
}
printf("\n");
//---|---|---
if (i < row - 1)
{
//printf("---|---|---\n");
for (j = 0; j < col; j++)
{
printf("---");
if (j < col - 1)
printf("|");
}
printf("\n");
}
}
}
void player_move(char board[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
printf("玩家下棋:>\n");
while (1)
{
printf("请输入要下棋的坐标:>");
scanf_s("%d %d", &x, &y);
//1.坐标的合法性
//2.坐标是否被占用
if (x >= 1 && x <= row && y >= 1 && y <= col)
{
if (board[x - 1][y - 1] == ' ')
{
board[x - 1][y - 1] = '*';
break;
}
else
{
printf("该坐标被占用,请重新输入\n");
}
}
else
{
printf("坐标非法,重新输入\n");
}
}
}
//
//电脑随机下棋
//
void computer_move(char board[ROW][COL], int row, int col)
{
printf("电脑下棋:>\n");
//0~32726
//%3-->0~2
while (1)
{
int x = rand() % row;
int y = rand() % col;
if (board[x][y] == ' ')
{
board[x][y] = '#';
break;
}
}
}
//如果棋盘满了,返回1
//不满,返回0
static int is_full(char board[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
int j = 0;
for (j = 0; j < col; j++)
{
if (' ' == board[i][j])
{
return 0;
}
}
}
return 1;
}
char is_win(char board[ROW][COL], int row, int col)
{
int i = 0;
for (i = 0; i < row; i++)
{
if (board[i][0] == board[i][1] && board[i][1] == board[i][2] && board[i][0] != ' ')
{
return board[i][0];
}
}
for (i = 0; i < col; i++)
{
if (board[0][i] == board[1][i] && board[1][i] == board[2][i] && board[0][i] != ' ')
{
return board[0][i];
}
}
if (board[0][0] == board[1][1] && board[1][1] == board[2][2] && board[1][1] != ' ')
{
return board[1][1];
}
if (board[0][2] == board[1][1] && board[1][1] == board[2][0] && board[1][1] != ' ')
{
return board[1][1];
}
//判断平局
if (is_full(board, row, col) == 1)
{
return 'Q';
}
//继续
return 'C';
}