三子棋小游戏

 游戏设计与实现过程的简单讲解。      

      游戏的话就要有菜单让人选择玩或是退出。这样就至少要有两个选择,那么就可以用到switch分支语句了。

      如果选择玩游戏,进入游戏,首先就要有棋盘。通过创建一个二维数组来创建一个简单的三行三列的格子当做棋盘。由于每一行每一列都是相同的,所以用两个for循环就OK了。对棋盘进行初始化。将棋盘每一个格子设置为存放一个空格‘ ’,既方便后边输入棋子又方便输入棋子时判断坐标是否已被占用。

      棋盘创建好了就是下棋的过程了,先是玩家走或者电脑走(由你自己决定)。而下棋的过程是通过输入坐标来实现。将代表玩家或电脑的棋子存放到坐标对应的位置就可以了。

      输入的坐标可分为合法坐标和非法坐标(1、坐标超出了棋盘   2、坐标已经被占用)。可以在输入时做判断。

      玩家输入坐标时将横纵坐标的值限定在大于等于1小于等于3之间(代码中是用数组的下标来表示的,所以是0,1,2),使其坐标不会超出棋盘。两个for循环就可以实现这个过程。判断坐标是否被占用,只需判断输入坐标所对应位置是不是空格‘ ’就行了。

      电脑的输入坐标是随机的,可能会输入非法坐标,就需要重新输入,所以电脑输入应该是一个循环的过程。在循环里边判断,如果是非法坐标,就得重新输入了。为了保证电脑在输入的随机坐标在棋盘内,可以通过将随机数模3(对3取余)的方法来限定下标为0,1,2的三个数中的一个。

      最后就是判断输赢了。有四种情况(玩家赢、电脑赢、平局、还没有下完)

玩家赢:横着、竖着或是斜着连续三个都是玩家的棋子。

电脑赢:横着、竖着或是斜着连续三个都是电脑的棋子。

平局:在棋盘已经满了的情况下不存在有连续三个棋子属于同一个玩家。

还没有下完:任意一个坐标对应的位置存放的是空格‘ ’。

 

接下来是完整的代码:

game.h部分

#ifndef __GAME_H__
#define __GAME_H__

#include <stdio.h>
#include <stdlib.h>
#include <string.h>


#define ROWS 3    //定义一个常变量ROWS
#define COLS 3     //定义一个常变量COLS 


void init_board(char board[ROWS][COLS], int row, int col);
void display_board(char board[ROWS][COLS], int row, int col);
void player_move(char board[ROWS][COLS], int row, int col);
void computer_move(char board[ROWS][COLS], int row, int col);
char check_win(char board[ROWS][COLS], int row, int col);

#endif

game.c部分 

#include "game.h"

void init_board(char board[ROWS][COLS], int row, int col)//
{
    memset(board, ' ', row*col*sizeof(board[0][0]));
}


void display_board(char board[ROWS][COLS], 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 != 2)
        printf("---|---|---\n");
    }
}


void player_move(char board[ROWS][COLS], int row, int col) //通过创建坐标的方式实现玩家走的过程
{
    int x = 0;
    int y = 0;
    while (1)
    {
        printf("请输入坐标:>");
        scanf("%d%d", &x, &y);
        x--;
        y--;
        if (((x >= 0) && (x <= 2)) && ((y >= 0) && (y <= 2)))  //判定所输坐标是否在棋盘内
        {
            if (board[x][y] ==' ')                           //判断所输坐标是否已被占用
            {
                board[x][y] = '*';              //所输坐标为合法坐标,将代表玩家的棋子“*”放入坐标所指位置
                break;
            }
            else
            {
                printf("坐标有误,重新输入!");
            }
        }
        else
        {
            printf("坐标有误,请重新输入!");
        }
    }
}


void computer_move(char board[ROWS][COLS], int row, int col)  //实现电脑走的函数
{
    while (1)
    {
        int x = rand() % 3;      //随机一个数对3求余,所得余数(可能值为0,1,2)作为横坐标
        int y = rand() % 3;      //随机一个数对3求余,所得余数(可能值为0,1,2)作为纵坐标
        if (board[x][y] == ' ')
        {
            board[x][y] = '#';    //所输坐标为合法坐标,将代表电脑的棋子“#”放入坐标所指位置
            break;
        }
    }
}


static int is_full(char board[ROWS][COLS], 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 check_win(char board[ROWS][COLS], 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][1]!=' '))
                return board[i][1];
        }
        for (i = 0; i < col; i++)
        {
            if ((board[0][i] == board[1][i])     //判断每一列的棋子是否同属于同一个玩家,同时不能算三个空格‘ ’的情况
            && (board[1][i] == board[2][i])
            && (board[1][i] != ' '))
                return board[1][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))          //棋盘满了但没有三个连续相同的情况(及平局的情况)
            {
                return 'q';
            }
            return ' ';
    }
}

test.c部分

test.c部分

#include <stdio.h>
#include <stdlib.h>
#include <time.h>


#include "game.h"


void game()
{
    char board[ROWS][COLS];    
    char ret = 0;
    init_board(board, ROWS, COLS);   //初始化棋盘
    display_board(board, ROWS, COLS);//显示棋盘
    srand((unsigned int)time(NULL));//对rand()函数进行申明
    while (1)
    {
        player_move(board, ROWS, COLS);
        if ((ret = check_win(board, ROWS, COLS)) != ' ')
            break;
        display_board(board, ROWS, COLS);
        computer_move(board, ROWS, COLS);
        if ((ret = check_win(board, ROWS, COLS)) != ' ')
            break;
        display_board(board, ROWS, COLS);
    }

    if (ret == '*')
    {
        printf("玩家赢\n");
    }
    else if (ret == '#')
    {
        printf("电脑赢\n");
    }
    else if (ret == 'q')
    {
        printf("平局\n");
    }
    display_board(board, ROWS, COLS);
}

void menu()           //菜单内容
{
    printf("*********************************\n");
    printf("****** 1、play    0、exit *******\n");//菜单的两个选择
    printf("*********************************\n");
}


int main()   //入口
{
    int input = 0;
    do
    {
        menu();     //进入菜单。 
        printf("请选择:>");
        scanf("%d", &input);
        switch (input)
        {
        case 1:                  //选择1
            game();              //进入游戏,开始玩游戏。具体玩的过程在game函数里边
            break;
        case 0:                  //选择0
            break;               //直接就退出了
        default:
            printf("选择错误\n");

        }
    } while (input);
    return 0;
}

 

 

  • 5
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值