UVA 1343 The Rotation Game

The Rotation Game

题意:

‘#’型棋盘上有8个1,8个2,8个3,可以往8个方向旋转

问中间8个格数字相同的最少旋转次数

输出字典序最小的方案数,并输出中间是哪个数

#include<cstdio>
#include<algorithm>

using namespace std;

int mov[8][7]={
    0,2,6,11,15,20,22,
    1,3,8,12,17,21,23,
    10,9,8,7,6,5,4,
    19,18,17,16,15,14,13,
    23,21,17,12,8,3,1,
    22,20,15,11,6,2,0,
    13,14,15,16,17,18,19,
    4,5,6,7,8,9,10
};
int pos[8]={6,7,8,11,12,15,16,17}; 
int rev[8]={5,4,7,6,1,0,3,2}; 
int a[24];
int maxd;
char order[10001];
int judge(int x){
    int sum=0;
    for(int i=0;i<8;i++)
        if(a[pos[i]]!=x) sum++;
    return sum;
}
int h(){
    return min(judge(1),min(judge(2),judge(3)));
}
void move(int i){
    int t=a[mov[i][0]];
    for(int j=0;j<6;j++)
        a[mov[i][j]]=a[mov[i][j+1]];
    a[mov[i][6]]=t;
}
bool dfs(int d){
    if(!judge(a[pos[0]])){
        order[d]='\0';
        puts(order);
        return true;
    }
    if(d+h()>maxd) return false;
    for(int i=0;i<8;i++){
        move(i);
        order[d]=char(i+'A');
        if(dfs(d+1)) return true;
        move(rev[i]);
    }
    return false;
} 
int main(){
    while(1){
        scanf("%d",&a[0]);
        if(!a[0])    return 0;
        for(int i=1;i<24;i++)    scanf("%d",&a[i]);
        if(!judge(a[pos[0]]))    puts("No moves needed");
        else    for(maxd=1;;maxd++)    if(dfs(0)) break;
        printf("%d\n",a[6]);
    }
}

 

posted @ 2017-10-18 22:30  一蓑烟雨任生平  阅读(156)  评论(0编辑  收藏  举报