3阶魔方的处理

#include<stdio.h>
#include<string.h>
using namespace std;
int T,deep;
char s[60] ;
int cent[7] = {5,23,26,29,32,50} ;//每个面的中心点
int ex[7][9] = {{1,2,3,4,6,7,8,9},
                {10,11,12,22,24,34,35,36},
                {13,14,15,25,27,37,38,39},
                {16,17,18,28,30,40,41,42},
                {19,20,21,31,33,43,44,45},
                {46,47,48,49,51,52,53,54}
               } ;
 
int get_h(){//以每个面与中心不同的数的和作为估值函数
    int res = 0 ;
    for(int i=0;i<6;i++){
        int c = 0 ;
        for(int j=0;j<8;j++){
            if(s[ex[i][j]]!=s[cent[i]])     c++ ;
        }
        res += c ;
    }
    return res ;
}
int wh[10], dd[10] ;
/*
         1  2  3
         4  5  6
         7  8  9
10 11 12 13 14 15 16 17 18 19 20 21
22 23 24 25 26 27 28 29 30 31 32 33
34 35 36 37 38 39 40 41 42 43 44 45
         46 47 48
         49 50 51
         52 53 54
*/
int ope[12][20] = {                     //用预处理的数组来代替每一种旋转,节约时间。
                   {1,4,7,13,25,37,46,49,52,21,33,45,10,11,12,24,36,35,34,22},
                   {45,33,21,1,4,7,13,25,37,52,49,46,34,22,10,11,12,24,36,35},
                   {7,8,9,16,28,40,48,47,46,36,24,12,13,14,15,27,39,38,37,25},
                   {36,24,12,7,8,9,16,28,40,48,47,46,37,25,13,14,15,27,39,38},
                   {9,6,3,19,31,43,54,51,48,39,27,15,16,17,18,30,42,41,40,28},
                   {39,27,15,9,6,3,19,31,43,54,51,48,40,28,16,17,18,30,42,41},
                   {42,30,18,3,2,1,10,22,34,52,53,54,19,20,21,33,45,44,43,31},
                   {52,53,54,42,30,18,3,2,1,10,22,34,43,31,19,20,21,33,45,44},
                   {15,14,13,12,11,10,21,20,19,18,17,16,1,2,3,6,9,8,7,4},
                   {18,17,16,15,14,13,12,11,10,21,20,19,7,4,1,2,3,6,9,8},
                   {37,38,39,40,41,42,43,44,45,34,35,36,46,47,48,51,54,53,52,49},
                   {34,35,36,37,38,39,40,41,42,43,44,45,52,49,46,47,48,51,54,53}
                  } ;
 
bool dfs(int d){
    char maze[60] ;
    int h = get_h();
    if(d+(h+11)/12 > deep)  return false ;//一次旋转最多使12个块归位
    if(h==0 && d==deep)  return true ;
    for(int i=0;i<12;i++){
        memcpy(maze,s,sizeof(s));
        for(int j=0;j<20;j++){
            s[ope[i][j]] = maze[ope[i^1][j]];
        }
        wh[d] = i/2 ;
        if((i&1)==0)   dd[d] = 1;
        else    dd[d] = -1 ;
        if(dfs(d+1))    return true ;
        memcpy(s,maze,sizeof(maze));
    }
}
 
 
int main(){
    //freopen("1in","r",stdin) ;
    //freopen("1out","w",stdout);
    scanf("%d",&T);
    while(T--){
        for(int i=1;i<=54;i++){
            scan(s[i]);
        }
        if(get_h() == 0){
            printf("0\n") ; continue ;
        }
        deep = 1 ;
        while(deep <= 5){
            if(dfs(0))  break ;
            deep ++ ;
        }
        if(deep > 5){
            printf("-1\n");
        }
        else{
            printf("%d\n",deep);
            for(int i=0;i<deep;i++){
                printf("%d %d\n",wh[i],dd[i]) ;
            }
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/qq_36225321/article/details/82937522