UVA-10384 推门游戏 题解答案代码 算法竞赛入门经典第二版

GitHub - jzplp/aoapc-UVA-Answer: 算法竞赛入门经典 例题和习题答案 刘汝佳 第二版

由于在迷宫中可以走的路线非常长,而且要求最短路线,因此这里使用了迭代加深搜索方式。

题目不难,每次行进的过程中注意墙和边缘的处理,然后走出迷宫的时候就表示得到结果了。

注意有推墙机制的存在,因此一个墙移动,有三个结点的数字会跟着移动:

  1. 当前位置减去当前墙

  2. 当前位置向前一个位置减去当前墙,增加前面的墙。

  3. 当前位置的前两个位置增加墙。

对应状态恢复的时候也要对这几个状态都恢复。

AC代码

cpp 复制代码
#include <stdio.h>
#include <string.h>

int arrWall[8][8];
int Steps[4][2] = {{0, -1}, {-1, 0}, {0, 1}, {1, 0}};
char StepConvert[4] = {'W', 'N', 'E', 'S'};
char StepRe[4] = {2, 3, 0, 1};
int stepArr[100000];

int stepMax;

bool outXY(int x, int y)
{
    if (x < 0 || x >= 4 || y < 0 || y >= 6)
        return true;
    return false;
}

void setWall(int x, int y, int i, bool set)
{
    int newX = x + Steps[i][0];
    int newY = y + Steps[i][1];
    int newnewX = newX + Steps[i][0];
    int newnewY = newY + Steps[i][1];
    int k = 1 << i;
    int rei = StepRe[i];
    int rek = 1 << rei;
    if (set)
    {
        arrWall[newX][newY] -= rek;
        arrWall[newX][newY] += k;
        arrWall[x][y] -= k;
        if (!outXY(newnewX, newnewY))
            arrWall[newnewX][newnewY] += rek;
        return;
    }
    arrWall[newX][newY] += rek;
    arrWall[newX][newY] -= k;
    arrWall[x][y] += k;
    if (!outXY(newnewX, newnewY))
        arrWall[newnewX][newnewY] -= rek;
}

bool computed(int x, int y, int stepNum)
{
    if (outXY(x, y))
        return true;
    if (stepNum >= stepMax)
        return false;
    int i, j, k, newX, newY;
    bool hasWall;
    for (i = 0; i < 4; ++i)
    {
        k = 1 << i;
        newX = x + Steps[i][0];
        newY = y + Steps[i][1];
        hasWall = false;
        // 有墙
        if (arrWall[x][y] & k)
        {
            hasWall = true;
            // 到边缘
            if (outXY(newX, newY))
                continue;
            // 再隔一层也有墙
            if (arrWall[newX][newY] & k)
                continue;
            setWall(x, y, i, true);
        }
        stepArr[stepNum] = i;
        if (computed(newX, newY, stepNum + 1))
            return true;
        // 回退墙
        if (hasWall)
            setWall(x, y, i, false);
    }
    return false;
}

int main()
{
    int x, y, t;
    int i, j, k;
    while (scanf("%d %d", &x, &y) == 2 && x != 0 && y != 0)
    {
        t = x;
        x = y;
        y = t;
        x = x - 1;
        y = y - 1;
        memset(arrWall, 0, sizeof(arrWall));
        for (i = 0; i < 4; ++i)
        {
            for (j = 0; j < 6; ++j)
                scanf("%d", &arrWall[i][j]);
        }
        for (i = 0;; ++i)
        {
            stepMax = i;
            if (computed(x, y, 0))
                break;
        }
        for (j = 0; j < i; ++j)
            putchar(StepConvert[stepArr[j]]);
        putchar('\n');
    }
    return 0;
}
相关推荐
UIU1144 小时前
P1233 [ICPC 2001 Taejon R] 木棍加工
数据结构·c++·算法·动态规划
论文复现现场5 小时前
WRF、FEA 能用 L40S 加速吗?求解器检查、断点恢复与长期运行
java·数据库·算法·wrf·有限元分析·gpu计算·断点续算
ZhengEnCi5 小时前
用 AI 写代码为什么拼到最后还是拼人:算力瓶颈与领域专家提示词的本质差异
算法·架构
秋天的怀念_David6 小时前
第二十一夜 · 数字黑洞与西西弗斯的惩罚
java·程序人生·算法
碧海银沙音频科技研究院7 小时前
在PC电脑上用Whisper→Marian算法实现离线语音翻译功能
算法·whisper
niyongsheng7 小时前
3D 装箱算法工程化:数据结构、放置启发式与支撑规则
数据结构·算法·rust
叉烧滑蛋9 小时前
B站台湾大学郭彦甫|MATLAB 学习笔记|04 变量与档案存取
数据结构
j7~9 小时前
【穷举、深搜与回溯算法】一棵决策树讲透全排列与子集
数据结构·c++·算法·leetcode·回溯·递归
傅科摆 _ py10 小时前
DP,贪心,堆和栈,二分力扣复习
开发语言·python·算法
Shaoshing11 小时前
LeetCode100 42.接雨水
java·算法·leetcode