hdu 1430+hdu 3567(预处理)

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1430

思路:由于只是8种颜色,所以标号就无所谓了,对起始状态重新修改标号为 12345678,对目标状态标号做相应的修改,先预处理出12345678到所有状态的路径,记录所有状态的pre值,直接输出即可。

  1 #include<iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<algorithm>

  5 #include<queue>

  6 #include<string>

  7 using namespace std;

  8 

  9 struct Node{

 10     char str[11];

 11     Node(){};

 12     Node(char _str[]){

 13         for(int i=0;i<8;i++){

 14             str[i]=_str[i];

 15         }

 16     }

 17 };

 18 

 19 int fac[]={1,1,2,6,24,120,720,5040,40320};

 20 int Get_Hash(Node &p)

 21 {

 22     int val=0;

 23     for(int i=0;i<8;i++){

 24         int cnt=0;

 25         for(int j=0;j<i;j++){

 26             if(p.str[j]>p.str[i])cnt++;

 27         }

 28         val+=cnt*fac[i];

 29     }

 30     return val;

 31 }

 32 

 33 void Move_A(Node &p)

 34 {

 35     reverse(p.str,p.str+8);

 36 }

 37 

 38 void Move_B(Node &p)

 39 {

 40     char ch=p.str[3];

 41     for(int i=3;i>=1;i--)p.str[i]=p.str[i-1];

 42     p.str[0]=ch;

 43     ch=p.str[4];

 44     for(int i=4;i<=6;i++)p.str[i]=p.str[i+1];

 45     p.str[7]=ch;

 46 }

 47 

 48 void Move_C(Node &p)

 49 {

 50     swap(p.str[1],p.str[2]);

 51     swap(p.str[5],p.str[6]);

 52     swap(p.str[1],p.str[5]);

 53 }

 54 

 55 

 56 int pre[400000],ans[400000];

 57 bool mark[400000];

 58 

 59 void BFS()

 60 {

 61     queue<Node>que;

 62     que.push(Node("12345678"));

 63     memset(mark,false,sizeof(mark));

 64     mark[0]=true;

 65     while(!que.empty()){

 66         Node p=que.front();

 67         que.pop();

 68         int p_val=Get_Hash(p);

 69         Node q(p);

 70         Move_A(q);

 71         int q_val=Get_Hash(q);

 72         if(!mark[q_val]){

 73             mark[q_val]=true;

 74             pre[q_val]=p_val;

 75             ans[q_val]='A';

 76             que.push(q);

 77         }

 78         q=p;

 79         Move_B(q);

 80         q_val=Get_Hash(q);

 81         if(!mark[q_val]){

 82             mark[q_val]=true;

 83             pre[q_val]=p_val;

 84             ans[q_val]='B';

 85             que.push(q);

 86         }

 87         q=p;

 88         Move_C(q);

 89         q_val=Get_Hash(q);

 90         if(!mark[q_val]){

 91             mark[q_val]=true;

 92             pre[q_val]=p_val;

 93             ans[q_val]='C';

 94             que.push(q);

 95         }

 96     }

 97 }

 98 

 99 char S[11],T[11];

100 int SS[11];

101 int main()

102 {

103     BFS();

104     while(~scanf("%s%s",S,T)){

105         for(int i=0;i<8;i++)SS[S[i]-'1']=i;

106         for(int i=0;i<8;i++)T[i]=SS[T[i]-'1']+'1';

107         Node p=Node(T);

108         int val=Get_Hash(p);

109         string ss="";

110         while(val){

111             ss+=ans[val];

112             val=pre[val];

113         }

114         reverse(ss.begin(),ss.end());

115         cout<<ss<<endl;

116     }

117     return 0;

118 }

119 

120 

121 

122 

123 

124 

125 

126 

127 

128 

129 

130     
View Code

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=3567

思路:因为这题有一个特殊的点X,所以枚举X的位置,打出9张前驱表,用魔板题一样的方法将两个状态的对应标号转化,输出就好了。

  1 #include<iostream>

  2 #include<cstdio>

  3 #include<cstring>

  4 #include<string>

  5 #include<algorithm>

  6 #include<queue>

  7 using namespace std;

  8 

  9 struct Node{

 10     int map[3][3];

 11     int x,y;

 12     Node(){}

 13     Node(char *str){

 14         for(int i=0,xx=0,yy=0;str[i];i++){

 15             map[xx][yy]=str[i];

 16             if(str[i]=='X'){ x=xx,y=yy; }

 17             yy++;

 18             if(yy==3)xx++,yy=0;

 19         }

 20     }

 21 }S;

 22 

 23 int fac[]= {1,1,2,6,24,120,720,5040,40320};

 24 //康拓展开

 25 int Get_Hash(Node &p)

 26 {

 27     char str[11];

 28     int val=0;

 29     for(int i=0;i<3;i++){        

 30         for(int j=0;j<3;j++){

 31         str[i*3+j]=p.map[i][j];

 32         int cnt=0;

 33         for(int k=i*3+j-1;k>=0;k--){

 34             if(str[k]>str[i*3+j])cnt++;

 35         }

 36         val+=fac[i*3+j]*cnt;

 37         }

 38     }

 39     return val;

 40 }

 41 

 42 int dir[4][2]={{1,0},{0,-1},{0,1},{-1,0}};

 43 char Dir[5]="dlru";

 44 int pre[11][400000];

 45 char ans[11][400000];

 46 bool mark[400000];

 47 

 48 void bfs(int x)

 49 {

 50     memset(pre[x],-1,sizeof(pre[x]));

 51     memset(mark,false,sizeof(mark));

 52     queue<Node>que;

 53     que.push(S);

 54     mark[Get_Hash(S)]=true;

 55     while(!que.empty()){

 56         Node p=que.front();

 57         que.pop();

 58         int p_val=Get_Hash(p);

 59         for(int i=0;i<4;i++){

 60             Node q=p;

 61             q.x=p.x+dir[i][0],q.y=p.y+dir[i][1];

 62             if(q.x<0||q.x>=3||q.y<0||q.y>=3)continue;

 63             q.map[p.x][p.y]=q.map[q.x][q.y];

 64             q.map[q.x][q.y]='X';

 65             int q_val=Get_Hash(q);

 66             if(mark[q_val])continue;

 67             mark[q_val]=true;

 68             pre[x][q_val]=p_val;

 69             ans[x][q_val]=Dir[i];

 70             que.push(q);

 71         }

 72     }

 73 }

 74 

 75 char str[11];

 76 int num[11];

 77 int main()

 78 {

 79     S=Node("X12345678");

 80     bfs(0);

 81     S=Node("1X2345678");

 82     bfs(1);

 83     S=Node("12X345678");

 84     bfs(2);

 85     S=Node("123X45678");

 86     bfs(3);

 87     S=Node("1234X5678");

 88     bfs(4);

 89     S=Node("12345X678");

 90     bfs(5);

 91     S=Node("123456X78");

 92     bfs(6);

 93     S=Node("1234567X8");

 94     bfs(7);

 95     S=Node("12345678X");

 96     bfs(8);

 97 

 98     int _case,p,t=1;

 99     scanf("%d",&_case);

100     while(_case --){

101         scanf("%s", str);

102         for(int i = 0, j = 0; i <= 8; i ++ ){

103             if(str[i] != 'X') num[str[i] - '0'] = j ++;

104             else p = i;

105         }

106         scanf("%s", str);

107         for(int i=0;i<=8;i++){

108             if(str[i]=='X')continue;

109             str[i]=num[str[i]-'0']+'1';

110         }

111         S=Node(str);

112         int val=Get_Hash(S);

113         string ss="";

114         while(val!=-1){

115             ss+=ans[p][val];

116             val=pre[p][val];

117         }

118         reverse(ss.begin(), ss.end());

119         printf("Case %d: %d\n",t++,ss.size()-1);

120         for(int i=1;i<ss.size();i++)cout<<ss[i];

121         cout<<endl;

122     }

123     return 0;

124 }
View Code

 

你可能感兴趣的:(HDU)