(部分系统可能会报错#include <termio.h>,请自行替换头文件进行)

#include <iostream>
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <ctime>
#include <termio.h>
#include <iomanip>
#define clear() cout << "\033c" << flush
using namespace std;

int num[10][10];
int rd, tme;
bool validMove;

int getch() // 不回显函数
{
    struct termios nts, ots;
    // 得到当前终端(0表示标准输入)的设置
    if (tcgetattr(0, &ots) < 0) return EOF;
    // 设置终端为Raw原始模式,该模式下所有的输入数据以字节为单位被处理
    nts = ots;
    cfmakeraw(&nts); 
    // 设置上更改之后的设置
    if (tcsetattr(0, TCSANOW, &nts) < 0) return EOF;
    // 设置还原成老的模式
    int cr;
    cr = getchar();
    if (tcsetattr(0, TCSANOW, &ots) < 0)  return EOF;
    return cr;
}

void intro() // 游戏规则展示
{
    cout << "***********************************************************" << endl;
    cout << "欢迎来到 数字华容道 游戏~" << endl;
    cout << "在这个游戏里会有一个 4*4 的表格,每个网格中有一个1~15之间的数" << endl;
    cout << "可以选择 w、s、a、d,上下左右的滑动,移动数" << endl;
    cout << "当按大小顺序从左到右、从上到下排列好所有的数,游戏结束!" << endl; 
    cout << "点击【ENTER】开始游戏" << endl;
    cout << "点击【ESC】退出游戏" << endl;
    cout << "***********************************************************" << endl;
}

void init() // 初始化网格
{
    int a[20] = {};
    for (int i = 1; i <= 15; i++)
    {
        a[i] = i;
    }
    srand(time(0));
    random_shuffle(a + 1, a + 15 + 1);
    int cnt = 0;
    for (int i = 1; i <= 15; i++)
    {
        for (int j = i+1; j <= 15; j++)
        {
            if (a[i] > a[j]) // 逆序数对个数
            {
                cnt++;
            }
        }
    }
    if (cnt % 2 == 1) // 逆序数对为奇数无解,减少一个
    {
        for (int i = 1; i <= 14; i++)
        {
            if (a[i] > a[i+1])
            {
                swap(a[i], a[i+1]);
                break;
            }
        }
    }
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            num[i][j] = a[(i-1)*4+j];
        }
    }
}

void drawBoard() // 打印当前表格
{
    // 输出上边框
    cout << "  ╔";
    for (int i = 1; i <= 4 - 1; i++) cout << "════╤";
    cout << "════╗\n";
    // 输出中间部分
    for (int i = 1; i <= 4; i++) // 行
    {
        cout << "  ║";
        for (int j = 1; j <= 4; j++) // 列
        {
            if (num[i][j] >= 10)
                cout << " " << num[i][j] << " "; 
            else if (num[i][j] != 0)
                cout << "  " << num[i][j] << " ";
            else
                cout << "    ";
            if (j != 4)
                cout << "│";
            else
                cout << "║";
        }
        cout << " \n";
        // 输出下边框
        if (i != 4)
        {
            cout << "  ╟";
            for (int i = 1; i <= 4 - 1; i++) cout << "────┼";
            cout << "────╢\n";
        }
        else
        {
            cout << "  ╚";
            for (int i = 1; i <= 4 - 1; i++) cout << "════╧";
            cout << "════╝\n";
        }
    }
}

bool gameOver()
{
    int a[20];
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            a[(i-1)*4+j] = num[i][j];
        }
    }
    for (int i = 1; i <= 15; i++)
    {
        if (a[i] != i)
        {
            return false;
        }
    }
    return true;
}

void MoveUp() // 向上移动
{   
    int x, y;
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            if (num[i][j] == 0)
            {
                x = i;
                y = j;
            }
        }
    }
    if (x == 4) validMove = false;
    else
    {
        validMove = true;
        swap(num[x][y], num[x+1][y]);
    }
}

void MoveDown() // 向下移动
{   
    int x, y;
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            if (num[i][j] == 0)
            {
                x = i;
                y = j;
            }
        }
    }
    if (x == 1) validMove = false;
    else
    {
        validMove = true;
        swap(num[x][y], num[x-1][y]);
    }
}

void MoveLeft() // 向左移动
{   
    int x, y;
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            if (num[i][j] == 0)
            {
                x = i;
                y = j;
            }
        }
    }
    if (y == 4) validMove = false;
    else
    {
        validMove = true;
        swap(num[x][y], num[x][y+1]);
    }
}

void MoveRight() // 向右移动
{   
    int x, y;
    for (int i = 1; i <= 4; i++)
    {
        for (int j = 1; j <= 4; j++)
        {
            if (num[i][j] == 0)
            {
                x = i;
                y = j;
            }
        }
    }
    if (y == 1) validMove = false;
    else
    {
        validMove = true;
        swap(num[x][y], num[x][y-1]);
    }
}

void Win() // 玩家获胜
{
    cout << "**********************************" << endl;
    cout << "——————————— ROUND:" << rd << " ————————————" << endl;
    cout << "——————————— TIME:" << tme << " s———————————" << endl;
    cout << "——————————— 玩家获胜! ————————————" << endl;
    cout << "**********************************" << endl << endl;
    exit(0);
}

void game() // 开始游戏
{
    cout << "\033c" << flush;
    cout << "**********************************" << endl;
    cout << "—————————— Ready Go~ ————————————" << endl;
    cout << "**********************************" << endl;
    drawBoard(); // 打印棋盘
    
    char ch = 0;
    int sta = time(0);
    while (!gameOver()) // 当游戏没结束时
    {
        tme = time(0) - sta;
        // 按键 操作数 时间
        cout << "Key:" << ch << " Round:" << rd << " Time:" << tme << endl;
        cout << "Tips:" << endl;
        cout << "w —— 上移" << endl;
        cout << "s —— 下移" << endl;
        cout << "a —— 左移" << endl;
        cout << "d —— 右移" << endl;
        cout << "e —— 退出游戏" << endl;
        cout << "r —— 开始新游戏" << endl;
        cout << "选择以上指令!" << endl;
        
        ch = getch(); // 输入操作指令
        if (ch == 'w') MoveUp();
        else if (ch == 's') MoveDown();
        else if (ch == 'a') MoveLeft();
        else if (ch == 'd') MoveRight();
        else if (ch == 'e') exit(0);
        else if (ch == 'r') // 开始新游戏
        {
            sta = time(0); // 清空开始时间
            rd = 0; // 清空操作次数
            memset(num, 0, sizeof(num)); // 清空表格数据
            return; 
        }
        else
        {
            cout << endl << "———————输入有误,请重新输入指令!———————" << endl << endl;
            continue;
        }
        cout << "\033c" << flush;
        drawBoard(); // 打印棋盘
        if (validMove) rd++; // 记录操作次数
    }
    Win();
}

int main()
{
    while (true)
    {
        intro(); // 游戏规则展示
        char ch = getch(); // 不回显函数,当用户按下某个字符时,函数自动读取,无需按回车
        if (ch == 13) // CR回车的ascii是13
        {
            init(); //初始化方格数据
            game(); // 开始游戏
        }
        else if (ch == 27) // ESC的ascii是27
        {
            cout << "退出游戏!" << endl;
            break;
        }
        else  cout << "输入有误,请再次输入!" << endl;
    }
    return 0;
}

C++数字华容道,免费复制相关推荐

  1. 超赞的贪吃蛇、吃豆人和数字华容道等童年小游戏1行Python代码就能玩

    今天分享一个有趣的Python游戏库freegames,它包含20余款经典小游戏,像贪吃蛇.吃豆人.乒乓.数字华容道等等,依托于标准库Turtle. 我们不仅可以通过1行代码进行重温这些童年小游戏,还 ...

  2. 【数字华容道】一、核心

    寒假的时候看最强大脑. 有些项目看的我也想试试,就在豌豆荚上搜索数字华容道,找到一个下载安装后,发现面丑就算了,自适应没有做好,玩不了就删掉了. 想了想这个游戏的逻辑,好像很简单,那自己做一个吧. 如 ...

  3. 数字华容道java_从零开发HarmonyOS(鸿蒙)手机小游戏——数字华容道

    前言 2月16号HarmonyOS2.0手机开发者Beta版已经发布了,作为"1+8+N"战略的重要入口和生态核心,怎么能少得了手机应用开发呢,今天将由深鸿会深大学习小组(Zzt_ ...

  4. 从零开发HarmonyOS(鸿蒙)手机小游戏——数字华容道

    HarmonyOS(鸿蒙)手机第一个小游戏app--数字华容道 前言 概述 正文 创建项目 实现初始界面布局 实现数字的随机打乱 实现滑动或点击调换数字 实现游戏成功界面 源代码 结语 前言 2月16 ...

  5. 鸿蒙手游——数字华容道

    HarmonyOS2.0手机开发者Beta版已经发布了,作为"1+8+N"战略的重要入口和生态核心,怎么能少得了手机应用开发呢,今天将由深鸿会深大学习小组(Zzt_01-23)从零 ...

  6. Qt小游戏之数字华容道(百行代码搭雏形,可玩;含源码+注释)

    文章目录 一.数字华容道,样图如下 二.废话少说直接上代码 1.首先是代码文件分析 2.CLabel的源码 3.CMainWindow的源码 4.main文件 总结 一.数字华容道,样图如下 相信大家 ...

  7. Python数字华容道--程序实现的创意数学小游戏

    下载链接:Python数字华容道--程序实现的创意数学小游戏-Python文档类资源-CSDN下载 当前的数学教育环境下,更强调的是数学素养的提升,本程序提供了一个免费的数学益智小游戏的学习和训练平台 ...

  8. 用Java写“数字华容道”小游戏,适合初学者的小游戏

    游戏资源放在这里: 链接:百度网盘 请输入提取码 提取码:9290 在这个小游戏里,我们不仅用到了JFrame类,还用到了继承的方法.所以在这里我们用IDEA实现,在一个包下创建一个华容道类,用来进行 ...

  9. Python游戏开发:最强大脑第一关,数字华容道

    前言 freegames是Apache2许可的Python游戏集合,旨在用于教育和娱乐,完全是开源的,我们只要引用编写就好,当前在最强大脑的舞台上的第一关就是数字华容道,好多人都栽在了上面,如果你也想 ...

最新文章

  1. 跟老齐学Python:轻松入门pdf
  2. DotNetNuke(DNN)升级攻略(DNN 4.3.7至DNN 4.6.0)
  3. 开发基于Web的RSS阅读器
  4. 《数据结构》知识点Day_03
  5. BZOJ-3531-旅行
  6. 剑指offer:合并两个排序的链表
  7. Android studio导入support-v4.jar
  8. c语言中循环结构的作用,C语言中对于循环结构优化的一些入门级方法简介
  9. 这 6 个开源工具 yyds
  10. 直接安装的Qt 5如何调试到源码中
  11. 图像检索代码python_python-图像检索
  12. 【岗位技能要求】人工智能+Python
  13. 【人工智能行业大师访谈4】吴恩达采访Yoshua Bengio
  14. window.print();去除页眉页脚及网址。
  15. mac 安装 Adobe CC XD
  16. 怎样将表格拆分为两个
  17. C语言中exit(0)、exit(1)、exit(2)有什么不同?
  18. Excel 筛选重复值和删除重复值的异同
  19. 此计算机无法访问移动网络,IT教程:为什么打电话显示无法访问移动网络
  20. STM32 SPI 软件NSS和硬件NSS解读

热门文章

  1. 大家好!欢迎加入QQ技术交流群。
  2. 神经网络之ResNet模型的实现(Python+TensorFlow)
  3. Twitter(二)
  4. Windows10系统的Superfetch服务
  5. 如何把Geohash的值解码成经度纬度?
  6. 不知道同声传译软件哪个好?这篇文章分享给你三个同声传译软件
  7. R语言:for循环使用小结
  8. 【教程】ENVI主成分分析详解
  9. kswapd0进程在CentOS下CPU占用率过高
  10. 分布式架构的发展和演进之路