zoukankan      html  css  js  c++  java
  • 紫书搜索 例题7-12 UVA

    题目链接:

    https://vjudge.net/problem/UVA-1343

    题意:

    数字1,2,3都有八个,求出最少的旋转次数使得图形中间八个数相同。
    旋转规则:对于每一长行或每一长列,每次旋转就是将数据向头的位置移动一位,头上的数放置到尾部。若次数相同,则找出字典序最小旋转次序。
    输入是从上到下,从左向右,注意方向

    题解:

    代码:

     1 #include <bits/stdc++.h>
     2 using namespace std;
     3 typedef long long ll;
     4 #define MS(a) memset(a,0,sizeof(a))
     5 #define MP make_pair
     6 #define PB push_back
     7 const int INF = 0x3f3f3f3f;
     8 const ll INFLL = 0x3f3f3f3f3f3f3f3fLL;
     9 inline ll read(){
    10     ll x=0,f=1;char ch=getchar();
    11     while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
    12     while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
    13     return x*f;
    14 }
    15 //////////////////////////////////////////////////////////////////////////
    16 const int maxn = 1e5+10;
    17 
    18 int maxd,ok,a[50];
    19 char ans[maxn];
    20 int line[8][7] = {
    21     {0,2,6,11,15,20,22},
    22     {1,3,8,12,17,21,23},
    23     {10,9,8,7,6,5,4},
    24     {19,18,17,16,15,14,13}
    25 };
    26 
    27 int rev[8] = {5,4,7,6,1,0,3,2}; // 通过A,B,C,D,反推其他方向。指向反向,用来还原现场。  
    28 int final[8] = {6,7,8,11,12,15,16,17}; // 最后答案要求的点  
    29 
    30 void init(){ // 反推方向
    31     for(int i=4; i<8; i++)
    32         for(int j=0; j<=6; j++)
    33             line[i][j] = line[rev[i]][6-j];
    34 }
    35 
    36 bool is_final(){
    37     int k = a[final[0]];
    38     for(int i=1; i<8; i++)
    39         if(a[final[i]]!=k) return false;
    40     return true;
    41 }
    42 
    43 void move(int k){
    44     int tmp = a[line[k][0]];
    45     for(int i=1; i<7; i++)
    46         a[line[k][i-1]] = a[line[k][i]];
    47     a[line[k][6]] = tmp;
    48 }
    49 
    50 int diff(int x){
    51     int cnt = 0;
    52     for(int i=0; i<8; i++)
    53         if(x != a[final[i]])
    54             cnt++;
    55     return cnt;
    56 }
    57 
    58 int h(){ //估值函数  
    59     return min(min(diff(1),diff(2)),diff(3));
    60 }
    61 
    62 void dfs(int cur){
    63     if(is_final()){
    64         ans[cur] = '';
    65         cout << ans << endl;
    66         ok = 1;
    67         return ;
    68     }
    69 
    70     if(cur+h() > maxd) return ; //剪枝
    71     for(int i=0; i<8; i++){
    72         ans[cur] = 'A'+i;
    73         move(i);
    74         dfs(cur+1);
    75         if(ok) return ;
    76         move(rev[i]); // 还原现场  
    77     }
    78 }
    79 
    80 int main(){
    81     init();
    82     while(scanf("%d",&a[0]) && a[0]){
    83         for(int i=1; i<24; i++) a[i]=read();
    84         ok = 0;
    85         if(is_final())
    86             puts("No moves needed");
    87         else{
    88             for(maxd=1; ; maxd++){
    89                 dfs(0);
    90                 if(ok) break;
    91             }
    92         }
    93         cout << a[6] << endl; // 最终的颜色 
    94     }
    95 
    96     return 0;
    97 }
  • 相关阅读:
    HDU 4069 Squiggly Sudoku
    SPOJ 1771 Yet Another NQueen Problem
    POJ 3469 Dual Core CPU
    CF 118E Bertown roads
    URAL 1664 Pipeline Transportation
    POJ 3076 Sudoku
    UVA 10330 Power Transmission
    HDU 1426 Sudoku Killer
    POJ 3074 Sudoku
    HDU 3315 My Brute
  • 原文地址:https://www.cnblogs.com/yxg123123/p/6827606.html
Copyright © 2011-2022 走看看