第一眼看到这题就直接BFS爆搜,第一发爆了内存,傻逼了忘标记了,然后就改,咋标记呢。
然后想到用map函数,就8!个不同的排列,换成字符串用map标记。然后又交一发果断超时,伤心,最恨超时,还不如来个wa算了。
然后卡着了,后来上网上搜,要用康托展开,康托展开是什么鬼?然后学习了一下,就是个映射,感觉和map差不多。
http://blog.****.net/zhongkeli/article/details/6966805这个学习一下康托展开。
其实本题的关键不是康托展开,而是置换。
以12345678为起始状态开始搜它经过3种变换能到达的所有状态的最小步数,每搜到一个记录下来,可以用康托展开,也可以用C++ STL库里的map
所以只要搜一次就够了,然后记录。那么咋转置呢。举个列子 初态为65871234 目标态为87125463,那么初态和12345678比较,6和1对应,5和2对应
8和3对应......,所以目标态的8为初态的第三位,而初态的第三位对应12345678中的三,所以目标态第一位转为3,同理第2位转为4......
最后的到状态为34562817,所以只要知道12345678转为34562817的最小步数就为所求。
下面给两段代码一个是用map写的一个是用康托展开写的。map写的运行时间比较慢200多Ms,不过时间足够,题目好像是给了5s吧,
康托展开是46ms.
题目链接http://acm.hdu.edu.cn/showproblem.php?pid=1430;
1 #include<stdio.h>
2 #include<algorithm>
3 #include<iostream>
4 #include<string.h>
5 #include<stdlib.h>
6 #include<math.h>
7 #include<queue>
8 #include<stack>
9 #include<cstdio>
10 #include<map>
11 void bfs();
12 using namespace std;
13 void AA(char *p,char *q);
14 void BB(char *p,char *q);
15 void CC(char *p,char *q);
16 int N=50005;
17 map<string,int>my;
18 char t[10]="12345678";
19 char a[41000][100];//总共有8!的状态每个状态对应一个数然后用数组存变换的步奏
20 typedef struct pp
21 {
22
23 char ab[10];
24 int n;
25
26 } ss;//开结构体存步数。
27 int main(void)
28 {
29
30 int n,i,j,k,p,q;
31 char aa[10];
32 char bb[10];
33 char cc[10];
34 bfs();
35 while(scanf("%s %s",aa,bb)!=EOF)
36 {
37 int yu=0;
38 for(i=0; i<8; i++)
39 {
40 for(j=0; j<8; j++)
41 {
42 if(bb[i]==aa[j])
43 {
44 cc[yu++]=j+1+'0';
45 }
46 }
47 }
48 cc[8]='\0';
49 int sh=my[cc];
50 puts(a[sh]);
51 }
52 return 0;
53
54 }
55 void bfs()
56 {
57 int i,j,k,p,q,l;
58 ss ll,mm;
59 ll.n=1;
60 int v=1;
61 my[t]=v;//map标记并映射为一个数
62 v++;
63 strcpy(ll.ab,t);
64 queue<ss>que;
65 que.push(ll);
66 while(!que.empty())
67 {
68 mm=que.front();
69 que.pop();
70 ss pp;
71 AA(pp.ab,mm.ab);
72
73 if(my[pp.ab]==0)
74 {
75 my[pp.ab]=v;
76 strcpy(a[v],a[mm.n]);//接上一个所有的变化步数
77 l=strlen(a[v]);//最后加上本次的变换
78 a[v][l]='A';
79 pp.n=v;
80 v++;
81 que.push(pp);
82 }
83 BB(pp.ab,mm.ab);
84
85 if(my[pp.ab]==0)
86 {
87 my[pp.ab]=v;
88 strcpy(a[v],a[mm.n]);
89 l=strlen(a[v]);
90 a[v][l]='B';
91
92 pp.n=v;
93 v++;
94 que.push(pp);
95 }
96 CC(pp.ab,mm.ab);
97
98 if(my[pp.ab]==0)
99 {
100 my[pp.ab]=v;
101 strcpy(a[v],a[mm.n]);
102 l=strlen(a[v]);
103 a[v][l]='C';
104 pp.n=v;
105 v++;
106 que.push(pp);
107 }
108
109
110
111
112 }
113
114
115
116
117
118
119 }//三种不同的转换;
120 void AA(char *p,char *q)
121 {
122 int i,j,k;
123 p[0]=q[7];
124 p[1]=q[6];
125 p[2]=q[5];
126 p[3]=q[4];
127 p[4]=q[3];
128 p[5]=q[2];
129 p[6]=q[1];
130 p[7]=q[0];
131 p[8]='\0';
132 }
133
134 void BB(char *p,char *q)
135 {
136 int i,j,k;
137 p[0]=q[3];
138 p[1]=q[0];
139 p[2]=q[1];
140 p[3]=q[2];
141 p[4]=q[5];
142 p[5]=q[6];
143 p[6]=q[7];
144 p[7]=q[4];
145 p[8]='\0';
146 }
147
148 void CC(char *p,char *q)
149 {
150 p[0]=q[0];
151 p[1]=q[6];
152 p[2]=q[1];
153 p[3]=q[3];
154 p[4]=q[4];
155 p[5]=q[2];
156 p[6]=q[5];
157 p[7]=q[7];
158 p[8]='\0';
159 }
1 #include<stdio.h>
2 #include<algorithm>
3 #include<iostream>
4 #include<string.h>
5 #include<stdlib.h>
6 #include<math.h>
7 #include<queue>
8 #include<stack>
9 #include<cstdio>
10 int kt(char *p);
11 void bfs();
12 using namespace std;
13 void AA(char *p,char *q);
14 void BB(char *p,char *q);
15 void CC(char *p,char *q);
16 int as[10];
17 int N=50005;
18 bool vis[50005];
19 char t[10]="12345678";
20 char a[41000][100];
21 typedef struct pp
22 {
23 char ab[10];
24 int n;
25
26 } ss;
27 int main(void)
28 {
29 as[0]=1;
30 as[1]=1;
31 as[2]=2;
32 as[3]=6;
33 as[4]=24;
34 as[5]=120;
35 as[6]=720;
36 as[7]=5040;//康托展开预处理
37 int n,i,j,k,p,q;
38 char aa[10];
39 char bb[10];
40 char cc[10];
41 memset(vis,0,sizeof(vis));
42 bfs();
43 while(scanf("%s %s",aa,bb)!=EOF)
44 {
45 int yu=0;
46 for(i=0; i<8; i++)
47 {
48 for(j=0; j<8; j++)
49 {
50 if(bb[i]==aa[j])
51 {
52 cc[yu++]=j+1+'0';
53 }
54 }
55 }
56
57 int sh=kt(cc);
58
59 puts(a[sh]);
60 }
61
62 return 0;
63
64 }
65
66 int kt(char *p)//康托展开
67 {
68 int i,j;
69 int kk=0;
70 for(i=0; i<8; i++)
71 {
72 int yy=0;
73 for(j=i+1; j<8; j++)
74 {
75 if((p[i]-'0')>(p[j]-'0'))
76 {
77 yy++;
78 }
79 }
80 kk+=yy*as[7-i];
81
82
83 }
84 return kk;
85 }
86
87 void bfs()
88 {
89 int i,j,k,p,q,l;
90 ss ll,mm;
91 ll.n=0;
92 vis[0]=true;
93 strcpy(ll.ab,t);
94 queue<ss>que;
95 que.push(ll);
96 while(!que.empty())
97 {
98 mm=que.front();
99 que.pop();
100 ss pp;
101 AA(pp.ab,mm.ab);
102 int yy=kt(pp.ab);
103 if(!vis[yy])
104 {
105 vis[yy]=true;
106 strcpy(a[yy],a[mm.n]);
107 l=strlen(a[yy]);
108 a[yy][l]='A';
109 pp.n=yy;
110 que.push(pp);
111 }
112 BB(pp.ab,mm.ab);
113 yy=kt(pp.ab);
114 if(!vis[yy])
115 {
116 vis[yy]=true;
117 strcpy(a[yy],a[mm.n]);
118 l=strlen(a[yy]);
119 a[yy][l]='B';
120 pp.n=yy;
121 que.push(pp);
122 }
123 CC(pp.ab,mm.ab);
124 yy=kt(pp.ab);
125 if(!vis[yy])
126 {
127 vis[yy]=true;
128 strcpy(a[yy],a[mm.n]);
129 l=strlen(a[yy]);
130 a[yy][l]='C';
131 pp.n=yy;
132 que.push(pp);
133 }
134
135
136
137
138 }
139
140
141
142
143
144 }
145 void AA(char *p,char *q)
146 {
147 int i,j,k;
148 p[0]=q[7];
149 p[1]=q[6];
150 p[2]=q[5];
151 p[3]=q[4];
152 p[4]=q[3];
153 p[5]=q[2];
154 p[6]=q[1];
155 p[7]=q[0];
156 }
157
158 void BB(char *p,char *q)
159 {
160 int i,j,k;
161 p[0]=q[3];
162 p[1]=q[0];
163 p[2]=q[1];
164 p[3]=q[2];
165 p[4]=q[5];
166 p[5]=q[6];
167 p[6]=q[7];
168 p[7]=q[4];
169 }
170
171 void CC(char *p,char *q)
172 {
173 p[0]=q[0];
174 p[1]=q[6];
175 p[2]=q[1];
176 p[3]=q[3];
177 p[4]=q[4];
178 p[5]=q[2];
179 p[6]=q[5];
180 p[7]=q[7];
181 }