您的位置:首页 > 大数据 > 人工智能

【宽搜】The Clocks 时钟 (Usaco_Training 1.4)

2012-10-18 17:22 246 查看
The Clocks
IOI'94 - Day 2
Consider nine clocks arranged in a 3x3 array thusly:

|-------|    |-------|    |-------|
|       |    |       |    |   |   |
|---O   |    |---O   |    |   O   |
|       |    |       |    |       |
|-------|    |-------|    |-------|
A            B            C

|-------|    |-------|    |-------|
|       |    |       |    |       |
|   O   |    |   O   |    |   O   |
|   |   |    |   |   |    |   |   |
|-------|    |-------|    |-------|
D            E            F

|-------|    |-------|    |-------|
|       |    |       |    |       |
|   O   |    |   O---|    |   O   |
|   |   |    |       |    |   |   |
|-------|    |-------|    |-------|
G            H            I

The goal is to find a minimal sequence of moves to return all the dials to 12 o'clock. Nine different ways to turn the dials on the clocks are supplied via a table below; each way is called a move. Select for each move a number 1 through 9 which will cause the dials of the affected clocks (see next table) to be turned 90 degrees clockwise.

MoveAffected clocks1ABDE2ABC3BCEF4ADG5BDEFH6CFI7DEGH8GHI9EFHI

Example

Each number represents a time accoring to following table:

9 9 12       9 12 12       9 12 12        12 12 12      12 12 12
6 6 6  5 ->  9  9  9  8->  9  9  9  4 ->  12  9  9  9-> 12 12 12
6 3 6        6  6  6       9  9  9        12  9  9      12 12 12

[But this might or might not be the `correct' answer; see below.]

PROGRAM NAME: clocks

INPUT FORMAT

Lines 1-3:Three lines of three space-separated numbers; each number represents the start time of one clock, 3, 6, 9, or 12. The ordering of the numbers corresponds to the first example above.

SAMPLE INPUT (file clocks.in)

9 9 12
6 6 6
6 3 6

OUTPUT FORMAT

A single line that contains a space separated list of the shortest sequence of moves (designated by numbers) which returns all the clocks to 12:00. If there is more than one solution, print the one which gives the lowest number when the moves are concatenated (e.g., 5 2 4 6 < 9 3 1 1).

SAMPLE OUTPUT (file clocks.out)

4 5 8 9








这一题很明显可以用宽搜解决(后来看别人的解题报告才知道深搜也可以)

宽搜的话,就需要队列维护,并且要记录方案,这里记录方案的时候理论上可以用string和数组记录,但是频繁使用string,程序就变得异常的慢!所以后来改成了数组记录,并且宽搜的空间是很宝贵的,所以记录方案的数组开合适就可以了,我开的50,如果100的话Usaco就会提示错误(还是英文的,看了好久才明白)

hash的设计可以用stl的set或者自己设计hash均可

当然,这一题宽搜是可以剪枝的!由于题目钟表的特殊性,不管哪个方案,用4次就相当于没用,所以当当前方案在到4次的时候就可以剪枝了

Usaco对格式很苛刻就不用说了,不能有多余空格,要有一个回车

C++ Code

/*
ID: jiangzh15
TASK: clocks
LANG: C++ http://oijzh.cnblogs.com */
#include<cstdio>
#include<iostream>
#include<cstdlib>
#include<string>
#include<queue>
using namespace std;

const int kkk[]={1,1,4,16,64,256,1024,4096,16384,65536};//hash表中要用
const int ddd[10][10]={    //A B C D E F G H I
{0,0,0,0,0,0,0,0,0,0},
{0,1,1,0,1,1,0,0,0,0},//1        ABDE
{0,1,1,1,0,0,0,0,0,0},//2        ABC
{0,0,1,1,0,1,1,0,0,0},//3        BCEF
{0,1,0,0,1,0,0,1,0,0},//4        ADG
{0,0,1,0,1,1,1,0,1,0},//5        BDEFH
{0,0,0,1,0,0,1,0,0,1},//6        CFI
{0,0,0,0,1,1,0,1,1,0},//7        DEGH
{0,0,0,0,0,0,0,1,1,1},//8        GHI
{0,0,0,0,0,1,1,0,1,1},//9        EFHI
};
struct node{int a[10],step,c[50],way[10];};
queue<node> q;
node first;
bool h[262143+100];

int gethash(node x)
{
int sum=0;
for(int i=1;i<=9;i++)
sum+=x.a[i]*kkk[i];
return sum;
}

void check(node x)
{
for(int i=1;i<=9;i++)
if(x.a[i]!=0)return;
for(int i=1;i<=x.step-1;i++) printf("%d ",x.c[i]);
printf("%d\n",x.c[x.step]);
exit(0);
}

int main()
{
freopen("clocks.in","r",stdin);
freopen("clocks.out","w",stdout);
int i,j;
for(i=1;i<=9;i++)
{scanf("%d",&first.a[i]);first.a[i]=(first.a[i]%12)/3;}
first.step=0;
check(first);
q.push(first);
while(!q.empty())
{
node newnd,nd=q.front();q.pop();
//printf("%d\n",nd.step);
for(i=1;i<=9;i++)
{
if(nd.way[i]>=3)continue;
newnd=nd;
newnd.step++;
newnd.way[i]++;
for(j=1;j<=9;j++)
{
newnd.a[j]+=ddd[i][j];
if(newnd.a[j]>=4)newnd.a[j]-=4;
}
newnd.c[newnd.step]=i;
if(!h[gethash(newnd)])
{
/*printf("step=%d    ",newnd.step);
for(int kk=1;kk<=newnd.step;kk++)
printf("%d ",newnd.c[kk]);
printf("\n");*/
check(newnd);
h[gethash(newnd)]=true;
q.push(newnd);
}
}
}
return 0;
}


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: