三子棋小游戏(C语言)
功能:
1.玩家与电脑玩:
2.玩家与玩家玩:
编程思想:
主要运用二维数组还有循环嵌套,大量的使用函数的调用;
每一个模块相对独立起来,自定义相应函数的功能;
代码包含三个文件:
#include<game.h> 各个自定义函数的声明;
#include<game.h> 游戏功能的实现;
#include<Test.h> 游戏的框架和逻辑;
自定义打印棋盘,可以修改行列数:
#define ROW 3
#define COL 3
#include<game.h>文件
#define _CRT_SECURE_NO_WARNINGS 1
#ifndef __GAME_H__
#define __GAME_H__
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<time.h>
//自定义棋盘的行列数
#define ROW 3
#define COL 3
//函数的声明:
void InitBoard(char board[ROW][COL], int row, int col); //空格初始化棋盘数组(row,col此时是变量名,不再是标号);
void DisplayBoard(char board[ROW][COL],int row,int col);//棋盘打印;
void PlayerMove(char board[ROW][COL], int row, int col);//人机模式下玩家走;
void ComputerMove(char board[ROW][COL], int row,int col);//电脑走;
void Player1Move(char board[ROW][COL],int row,int col);//交互模式下Player1走
void Player2Move(char board[ROW][COL], int row, int col);//Player2走
char Judge(char board[ROW][COL],int row,int col);//输赢判断;
int DogFall(char board[ROW][COL], int row, int col);//判断平局(即棋盘满了还没有人赢)
#endif //__GAME_H__
该模块下主要是对调用函数的声明,头文件使用的声明;
include<Test.h> 文件, 游戏的框架和逻辑;
游戏菜单的打印
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdlib.h>
#include<stdlib.h>
#include"game.h"
void menu()
{
printf("***********************************\n");
printf("******* 1.Play. ********\n");
printf("******* 2.Mutual Play. ********\n");
printf("******* 0.Exit. ********\n");
printf("***********************************\n");
}
主函数:游戏框架
int main()
{
int input = 0;
srand((unsigned int)time(NULL)); //生成随机数
do
{
menu();
printf("\n请选择>>-:");
scanf("%d", &input);
switch (input)
{
case 1:
game();
break;
case 2:
Mutualgame();
break;
case 0:
printf("退出游戏,记得常玩!^-^\n");
break;
default:
printf("选择错误,亲重新选择……\n");
break;
}
} while (input);
system("pause");
return 0;
}
人机模式的游戏逻辑:
void game() //游戏模块独立出来
{
char board[ROW][COL] = { 0 };
char win = 0;
InitBoard(board, ROW, COL);
DisplayBoard(board,ROW,COL);
while (1)
{
PlayerMove(board, ROW, COL);
win = Judge(board, ROW, COL);
if (win != ' ')
break;
DisplayBoard(board, ROW, COL);
ComputerMove(board, ROW, COL);
win = Judge(board, ROW, COL);
if (win != ' ')
break;
DisplayBoard(board, ROW, COL);
}
if (win =='X')
printf("恭喜你,你赢了!\n");
else if (win == '0')
printf("哎呀呀,你输了,要加油呀!\n");
else if (win == '=')
printf("**平局**\n");
DisplayBoard(board, ROW, COL);
}
交互模式
void Mutualgame() //游戏模块独立出来
{
char board[ROW][COL] = { 0 };
char win = 0;
InitBoard(board, ROW, COL);
DisplayBoard(board, ROW, COL);
while (1)
{
Player1Move(board, ROW, COL);
win = Judge(board, ROW, COL);
if (win != ' ')
break;
DisplayBoard(board, ROW, COL);
Player2Move(board, ROW, COL);
win = Judge(board, ROW, COL);
if (win != ' ')
break;
DisplayBoard(board, ROW, COL);
}
if (win == 'X')
printf("恭喜Player1,你赢了!\n");
else if (win == '0')
printf("哎呀呀,恭喜Player2获胜!Player1输了,要加油呀!\n");
else if (win == '=')
printf("**平局**\n");
DisplayBoard(board, ROW, COL);
}
#include<game.h>游戏功能的实现
主要包含:
1.用空格初始化二维数组棋盘
2.打印棋盘(三子棋为例,边缘的线不打印)
3.玩家和电脑落子
4.Player1和Player2落子
5.遍历棋盘,看是否下满了(满了或者该位置有棋就不能下了)
6.判断输赢、平局
初始化数组并打印棋盘
#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include"game.h"
void InitBoard(char board[ROW][COL], int row, int col) //row,col此时是变量名,不再是标号;
{
//初始化棋盘数组
memset(&board[0][0], ' ', row * col * sizeof(board[0][0])); //调用库函数初始化
}
//打印棋盘:
void DisplayBoard(char board[ROW][COL], int row, int col)
{
int i = 0;
int j = 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");*/
for (j = 0; j < col; j++)
{
printf(" %c ",board[i][j]);
if(j<col-1)
printf("|");
}
printf("\n");
if (i < row - 1)
{
for (j = 0; j < col; j++)
{
printf("---");
if (j < col - 1)
printf("|");
}
}
printf("\n");
}
}
玩家和电脑走
//玩家放置棋子
void PlayerMove(char board[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
printf("玩家走>:");
while (1)
{
printf("请输入要放置棋子的坐标>>-:");
scanf("%d%d", &x, &y);
if (x >= 1 && x <= row && y >= 1 && y <= col)
{
//如果该位置放置了棋子,则不能在此输入坐标
if (board[x - 1][y - 1] == ' ')
{
board[x - 1][y - 1] = 'X';
break;
}
else
{
printf("这里有棋子了,不妨换个地方吧!^-^\n");
}
}
else
{
printf("输入错误,请重新输入,好好看看棋盘吧^-^\n\n");
}
}
}
//电脑走:
void ComputerMove(char board[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
printf("电脑走>>-:\n\n");
while (1)
{
x = rand() % row;
y = rand() % col;
if (board[x][y] == ' ')
{
board[x][y] = '0';
break;
}
}
}
Plryer1和Player2(逻辑和人机中的玩家一样)
void Player1Move(char board[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
printf("玩家1走>:");
while (1)
{
printf("请输入要放置棋子的坐标>>-:");
scanf("%d%d", &x, &y);
if (x >= 1 && x <= row && y >= 1 && y <= col)
{
if (board[x - 1][y - 1] == ' ')
{
board[x - 1][y - 1] = 'X';
break;
}
else
{
printf("这里有棋子了,不妨换个地方吧!^-^\n");
}
}
else
{
printf("输入错误,请重新输入,好好看看棋盘吧^-^\n\n");
}
}
}
void Player2Move(char board[ROW][COL], int row, int col)
{
int x = 0;
int y = 0;
printf("玩家2走>:");
while (1)
{
printf("请输入要放置棋子的坐标>>-:");
scanf("%d%d", &x, &y);
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\n");
}
}
}
遍历棋盘
//遍历棋盘,看是否满了:
static int DogFall(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++)
{
if (board[i][j] == ' ')
{
return 0;
}
}
}
return 1;
}
胜负判断
该处有待改进,只能判断三子棋输赢,即行列相同或者对角线相同
//判断每走一步的输赢:
char Judge(char board[ROW][COL], int row, int col)
{
int i = 0;
int j = 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 (j = 0; j < col; j++)
{
if (board[0][j] == board[1][j] && board[1][j] == board[2][j] && board[0][j] != ' ')
{
return board[0][j];
}
}
if (board[0][0] == board[1][1] && board[1][1] == board[2][2] && board[1][1] != ' ')
{
return board[0][0];
}
if (board[0][2] == board[1][1] && board[1][1] == board[2][0] && board[1][1] != ' ')
{
return board[0][2];
}
//判断平局:
if (DogFall(board, ROW, COL) == 1) //棋盘满了返回1.没满返回0;
{
return '=';
}
//没人赢,没有平局,游戏继续;
else
{
return ' ';
}
}
运行结果
玩家赢
电脑赢
Player1和Player2
这个游戏的高明之处不是让你赢,是让电脑赢;如果和电脑下了平局,你才能理解其中奥义-……