zoj - 1008 Gnome Tetravex

http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=1008

题目很长,读完后很容易理解错。题目中要求的不是移动三角形而是对整个矩形进行移动来达到目的!!!

题目读懂后就容易写了,很明显是dfs+回溯的题,注意相同的矩形可以存储在一块,可以方便dfs。

ac后发现运行时间竟达到5000+ms,还没超时,看到有0s过的,无奈,只能仰视~~Orz。。。

代码如下:

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
/*
注意不是选择方块或拼接三角形,是移动整个方块!!!
*/
int n, cur;
int map[30][4];
int count[30];
int result[30];

int dfs(int num, int n)
{
int i;
if(num == n*n) //放置完成
return 1;
for(i = 0; i < cur; i++) //从左向右,从上向下依次放方块
{
if(!count[i])
continue;
if(num % n != 0) //不是第一列的位置
{
if(map[i][3] != map[result[num-1]][1]) //放置第i个方块与左边放置的方块不匹配
continue;
}
if(num / n != 0) //不是第一行的位置
{
if(map[i][0] != map[result[num-n]][2]) //放置第i个方块与上边放置的方块不匹配
continue;
}
result[num] = i; //第i个方块可以放到num的位置
count[i]--;
if(dfs(num+1, n))
return 1;
else
count[i]++;
}
return 0;
}

int main()
{
int i, j, a, b, c, d, numofcases = 0, ok = 0;
while(scanf("%d", &n) && n)
{
cur = 0;
memset(count, 0, sizeof(count));
for(i = 0; i < n*n; i++)
{
scanf("%d%d%d%d", &a, &b, &c, &d);
for(j = 0; j < cur; j++) //相同的方块存在一块
{
if(map[j][0] == a && map[j][1] == b && map[j][2] == c && map[j][3] == d)
{
count[j]++;
break;
}
}
if(j == cur)
{
map[cur][0] = a;
map[cur][1] = b;
map[cur][2] = c;
map[cur][3] = d;
cur ++;
count[j]++;
}
}
if(!ok)
ok = 1;
else printf("\n");
if(dfs(0, n))
printf("Game %d: Possible\n", ++numofcases);
else printf("Game %d: Impossible\n", ++numofcases);
}
return 0;
}

 

posted @ 2012-03-04 18:31  枫萧萧  阅读(866)  评论(0编辑  收藏  举报