Holedox Moving
Time Limit: 5000MS   Memory Limit: 65536K
Total Submissions: 16980   Accepted: 4039

Description

During winter, the most hungry and severe time, Holedox sleeps in its lair. When spring comes, Holedox wakes up, moves to the exit of its lair, comes out, and begins its new life. 
Holedox is a special snake, but its body is not very long. Its lair is like a maze and can be imagined as a rectangle with n*m squares. Each square is either a stone or a vacant place, and only vacant places allow Holedox to move in. Using ordered pair of row and column number of the lair, the square of exit located at (1,1).

Holedox's body, whose length is L, can be represented block by block. And let B1(r1,c1) B2(r2,c2) .. BL(rL,cL) denote its L length body, where Bi is adjacent to Bi+1 in the lair for 1 <= i <=L-1, and B1 is its head, BL is its tail.

To move in the lair, Holedox chooses an adjacent vacant square of its head, which is neither a stone nor occupied by its body. Then it moves the head into the vacant square, and at the same time, each other block of its body is moved into the square occupied by the corresponding previous block.

For example, in the Figure 2, at the beginning the body of Holedox can be represented as B1(4,1) B2(4,2) B3(3,2)B4(3,1). During the next step, observing that B1'(5,1) is the only square that the head can be moved into, Holedox moves its head into B1'(5,1), then moves B2 into B1, B3 into B2, and B4 into B3. Thus after one step, the body of Holedox locates in B1(5,1)B2(4,1)B3(4,2) B4(3,2) (see the Figure 3).

Given the map of the lair and the original location of each block of Holedox's body, your task is to write a program to tell the minimal number of steps that Holedox has to take to move its head to reach the square of exit (1,1). 

Input

The input consists of several test cases. The first line of each case contains three integers n, m (1<=n, m<=20) and L (2<=L<=8), representing the number of rows in the lair, the number of columns in the lair and the body length of Holedox, respectively. The next L lines contain a pair of row and column number each, indicating the original position of each block of Holedox's body, from B1(r1,c1) to BL(rL,cL) orderly, where 1<=ri<=n, and 1<=ci<=m,1<=i<=L. The next line contains an integer K, representing the number of squares of stones in the lair. The following K lines contain a pair of row and column number each, indicating the location of each square of stone. Then a blank line follows to separate the cases.

The input is terminated by a line with three zeros.

Note: Bi is always adjacent to Bi+1 (1<=i<=L-1) and exit square (1,1) will never be a stone.

Output

For each test case output one line containing the test case number followed by the minimal number of steps Holedox has to take. "-1" means no solution for that case.

Sample Input

5 6 4
4 1
4 2
3 2
3 1
3
2 3
3 3
3 4 4 4 4
2 3
1 3
1 4
2 4
4 2 1
2 2
3 4
4 2 0 0 0

Sample Output

Case 1: 9
Case 2: -1

Hint

In the above sample case, the head of Holedox can follows (4,1)->(5,1)->(5,2)->(5,3)->(4,3)->(4,2)->(4,1)->(3,1)->(2,1)->(1,1) to reach the square of exit with minimal number of step, which is nine. 

Source

题意:在一个n*m的方格上,有一条长为L的蛇,由L个关节组成,每次蛇头不能碰到身体和石头,求最少多少步到达(1,1)这个位置.
这道题我不大会,参考了一下其他神犇的博客.
分析:如果没有身体这个限制,那么就是一道bfs的题,如果有身体这个限制,我们就要想办法记录下它的每个关节在哪个位置,下一次会往哪里走.
       显然,我们可以用一个结构体记录每个关节的位置,每个关节下一次走的位置就是它的上一个关节原来的位置,这样的话还是有一个问题:bfs需要一个vis数组记录曾经搜索过的状态,在这道题中我们该记录什么呢?头的位置肯定是要记录的,但是每个关节的位置记录不下来,空间会爆掉,那我们可以记录每个关节行走的方向,但是这样处理比较麻烦,于是我们记录每个关节关于它的后一个关节的相对运动方向.但是这样的话似乎要开一个很多维的数组,这样也实在是太麻烦了,于是可以很自然的想到状态压缩,可是我们有4个方向,压成二进制每位表示的不够啊,那么我们就每2位表示一节的方向就好了.
       有一个优化:由于vis数组很大,我们如果每次清空都会花费大量的时间,所以我们不再是赋值为0,1,而是看它是不是等于当前的tot(第tot组数据),这样就相当于是一个bool判断.
       不过这样还是会超时啊(要疯了!),那么就要用到搜索中常用的技巧了--启发式搜索,也就是A*,不过太麻烦了,就没写,以下是裸bfs代码:
#include <cstdio>
#include <queue>
#include <cstring>
#include <iostream>
#include <algorithm> using namespace std; int n, m, l,tot = ,a[][];
int vis[][][ << ],k;
int d[][] = {
-,,-,
,-,,
-,,-
}; int dx[] = { ,-,, }, dy[] = { ,,,- }; struct node
{
int x[], y[], cnt;
}; bool check(int x, int y, node u)
{
for (int i = ; i <= l; i++)
if (x == u.x[i] && y == u.y[i])
return false;
return true;
} int bfs(node x)
{
queue<node> q;
q.push(x);
while (!q.empty())
{
node u = q.front();
q.pop();
if (u.x[] == && u.y[] == )
return u.cnt;
for (int i = ; i < ; i++)
{
node v;
int tx = u.x[] + dx[i], ty = u.y[] + dy[i];
if (tx < || tx > n || ty < || ty > m || a[tx][ty])
continue;
if (!check(tx, ty, u))
continue;
u.x[] = tx, u.y[] = ty;
int zhuangtai = ;
for (int j = l; j >= ; j--)
{
v.x[j] = u.x[j - ];
v.y[j] = u.y[j - ];
if (j != l)
{
int temp = d[v.x[j] - v.x[j + ] + ][v.y[j] - v.y[j + ] + ];
zhuangtai |= (temp << ( - j * ));
}
}
if (vis[tx][ty][zhuangtai] == tot)
continue;
vis[tx][ty][zhuangtai] = tot;
v.cnt = u.cnt + ;
q.push(v);
}
}
return -;
} int main()
{
while (scanf("%d%d%d", &n, &m, &l) == )
{
memset(a, , sizeof(a));
int temp = ,tx,ty;
node init;
scanf("%d%d", &init.x[], &init.y[]);
for (int i = ; i <= l; i++)
{
scanf("%d%d", &init.x[i], &init.y[i]);
tx = init.x[i - ] - init.x[i] + ;
ty = init.y[i - ] - init.y[i] + ;
temp |= (d[tx][ty] << ( - (i - ) * ));
}
vis[init.x[]][init.y[]][temp] = tot;
scanf("%d", &k);
for (int i = ; i <= k; i++)
{
int aa, bb;
scanf("%d%d", &aa, &bb);
a[aa][bb] = ;
}
init.cnt = ;
printf("Case %d: %d\n", tot++, bfs(init));
} return ;
}

poj1324 Holedox Moving的更多相关文章

  1. poj 1324 Holedox Moving

    poj 1324 Holedox Moving 题目地址: http://poj.org/problem?id=1324 题意: 给出一个矩阵中,一条贪吃蛇,占据L长度的格子, 另外有些格子是石头, ...

  2. POJ 1324 Holedox Moving (状压BFS)

    POJ 1324 Holedox Moving (状压BFS) Time Limit: 5000MS Memory Limit: 65536K Total Submissions: 18091 Acc ...

  3. POJ 1324 Holedox Moving 搜索

    题目地址: http://poj.org/problem?id=1324 优先队列---A*的估价函数不能为蛇头到(1,1)的距离,这样会出错. 看了discuss,有大神说这题A*的估价函数为BFS ...

  4. UVALive 2520 Holedox Moving(BFS+状态压缩)

    这个题目在比赛的时候我们是没有做出来的,但是听到他们说进制哈希的时候,感觉真的是挺高端的,于是赛后开始补题,本着我的习惯在看题解之前自己再试着写一遍,我当时存储状态的方法是string + map,我 ...

  5. POJ - 1324 Holedox Moving (状态压缩+BFS/A*)

    题目链接 有一个n*m(1<=n,m<=20)的网格图,图中有k堵墙和有一条长度为L(L<=8)的蛇,蛇在移动的过程中不能碰到自己的身体.求蛇移动到点(1,1)所需的最小步数. 显然 ...

  6. ACM/ICPC 之 BFS+状态压缩(POJ1324(ZOJ1361))

    求一条蛇到(1,1)的最短路长,题目不简单,状态较多,需要考虑状态压缩,ZOJ的数据似乎比POj弱一些 POJ1324(ZOJ1361)-Holedox Moving 题意:一条已知初始状态的蛇,求其 ...

  7. HOJ题目分类

    各种杂题,水题,模拟,包括简单数论. 1001 A+B 1002 A+B+C 1009 Fat Cat 1010 The Angle 1011 Unix ls 1012 Decoding Task 1 ...

  8. BFS广搜题目(转载)

    BFS广搜题目有时间一个个做下来 2009-12-29 15:09 1574人阅读 评论(1) 收藏 举报 图形graphc优化存储游戏 有时间要去做做这些题目,所以从他人空间copy过来了,谢谢那位 ...

  9. poj 1324 状态压缩+bfs

    http://poj.org/problem?id=1324 Holedox Moving Time Limit: 5000MS   Memory Limit: 65536K Total Submis ...

随机推荐

  1. UITableView设计思想 考察

    整体使用了build模式:单是组织结构混乱:不符合人类思维. UITableViewDataSource:描述了View的要素个数情况:并担负了builder功能. UITableViewDelega ...

  2. 2017乌鲁木齐网络赛 j 题

    题目连接 : https://nanti.jisuanke.com/t/A1256 Life is a journey, and the road we travel has twists and t ...

  3. C++ Stack 与String

    // ConsoleApplication1.cpp : 此文件包含 "main" 函数.程序执行将在此处开始并结束. // #include "pch.h" ...

  4. 01_10_SERVLET如何连接Mysql数据库

    01_10_SERVLET如何连接Mysql数据库 1. 实现类 public void doGet(HttpServletRequest request, HttpServletResponse r ...

  5. iOS 打印系统字体

    NSArray * array = [UIFont familyNames]; for( NSString *familyName in array ){ printf( "Family: ...

  6. runtime实践之Method Swizzling

    利用 Objective-C 的 Runtime 特性,我们可以给语言做扩展,帮助解决项目开发中的一些设计和技术问题.这一篇,我们来探索一些利用 Objective-C Runtime 的黑色技巧.这 ...

  7. c++ 指针数组,输入4个季度的花费,计算出总花费

    #include <iostream> #include <array> #include <string> const int Seasons = 4; cons ...

  8. 【python】python安装和运行报错汇总

    本文主要用于汇总在python开发过程中遇到的各种环境.工具相关问题,便于后续遇到相关问题,及时搞定,持续更新. 一.安装pip失败,具体如下: 错误信息: python setup.py insta ...

  9. 【mysql】The server quit without updating PID file

      groupadd mysql useradd -r -g mysql mysql cd /usr/local/mysql chown -R mysql:mysql . scripts/mysql_ ...

  10. 多本Python极速入门最佳书籍,不可错过的Python学习资料!

    Python作为现在很热门的一门编程语言,介于Python的友好,许多的初学者都将其作为首选,为了帮助大家更好的学习Python,我筛选了2年内优秀的python书籍,个别经典的书籍扩展到5年内.   ...