爆搜题
用些技巧想办法把它写短咯
一次操作至多使中间8个数中最大相同的数的个数加一
估价函数设置为8-中间8个数中最多的相同的数的个数
#include <iostream>
#include <cstdio>
#include <cstring>
#define N 105
using namespace std;
inline int rd() {int r;scanf("%d",&r);return r;}
int a[N],o[N],pool[4],lim;
const int g[8][7] = {
1,3,7,12,16,21,23,
2,4,9,13,18,22,24,
11,10,9,8,7,6,5,
20,19,18,17,16,15,14,
24,22,18,13,9,4,2,
23,21,16,12,7,3,1,
14,15,16,17,18,19,20,
5,6,7,8,9,10,11
};
const int inv[] = {5,4,7,6,1,0,3,2};
const int key[] = {7,8,9,12,13,16,17,18};
void rotate(int x) {
int tmp = a[ g[x][0] ];
for (int i=1;i<7;i++) a[ g[x][i-1] ] = a[ g[x][i] ];
a[ g[x][6] ] = tmp;
}
int check() {
int ret = 0;
memset(pool,0,sizeof(pool));
for (int i=0;i<8;i++) pool[ a[ key[i] ] ]++;
for (int i=1;i<=3;i++) ret = max(ret, pool[i]);
return 8-ret;
}
bool dfs(int dep) {
if (dep > lim) {
if (check() == 0) {
for (int i=1;i<=lim;i++) putchar(o[i]+'A'-1);
putchar('\n');
printf("%d\n",a[7]);
return 1;
}
return 0;
}
if (check() + dep - 1 > lim) return 0;
for (int i=0;i<8;i++) {
rotate(i);
o[dep] = i+1;
if ( dfs(dep+1) ) return 1;
o[dep] = 0;
rotate(inv[i]);
}
return 0;
}
void solve() {
if (check() == 0) {
puts("No moves needed");
printf("%d\n",a[7]);
return ;
}
lim = 1;
while (!dfs(1)) lim++;
}
int main() {
for (;;) {
a[1] = rd();
if (!a[1]) break;
for (int i=2;i<=24;i++) a[i] = rd();
solve();
}
return 0;
}