• 紫书搜索 习题7-3 UVA


    题目链接:

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

    题意:

    给一副图,代表多米诺骨牌摆放方式,每两个连成一块牌,如0 0 对应1号排 0 1 对应2号排,问图可以代表几种摆放方式。

    题解:

    dfs,每个位置的牌不是竖就是横,枚举2个方向,最多枚举28块,O(2^28),加个剪枝,如果进入枚举下一行了,当前行还有没填上的,就直接回溯。

    代码:

      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 num[8][9],g[8][9];
     19 int res[10][10],vis[10][10],v[30];
     20 int dir[2][2] = {{1,0},{0,1}};
     21 int ans;
     22 
     23 void table(){
     24     int cnt = 1;
     25     for(int i=0; i<7; i++)
     26         for(int j=i; j<7; j++)
     27             num[i][j] = num[j][i] = cnt++;
     28 }
     29 
     30 bool ok(int x){
     31     for(int i=0; i<8; i++)
     32         if(vis[x][i] == 0) return false;
     33     return true;
     34 }
     35 
     36 void dfs(int x,int y,int nu){
     37     if(nu == 28){
     38         ans++;
     39         for(int i=0; i<7; i++){
     40             for(int j=0; j<8; j++)
     41                 printf("%4d",res[i][j]);
     42             puts("");
     43         }
     44         puts("");
     45         return ;
     46     }
     47 
     48     if(x==7) return ;
     49     if(y==8){
     50         if(!ok(x)) return ;  // 这一行没有都被覆盖,这种解不行,回溯
     51         dfs(x+1,0,nu);
     52         return ;
     53     }
     54 
     55     if(vis[x][y]){
     56         dfs(x,y+1,nu);
     57         return ;
     58     }
     59 
     60     for(int i=0; i<2; i++){
     61         if(i==0 && x==6) continue;
     62         if(i==1 && y==7) continue;
     63         int tx=x+dir[i][0], ty=y+dir[i][1];
     64         int k = num[g[x][y]][g[tx][ty]];
     65         if(vis[tx][ty]) continue;
     66         if(v[k]) continue;
     67         res[x][y] = res[tx][ty] = k;
     68         vis[x][y] = vis[tx][ty] = v[k] = 1;
     69         dfs(x,y+1,nu+1);
     70         vis[x][y] = vis[tx][ty] = v[k] = 0;
     71     }
     72 }
     73 
     74 int main(){
     75     table();
     76     int cas=0;
     77     while(~scanf("%d",&g[0][0])){
     78         MS(vis); MS(v); ans=0;
     79         if(cas) printf("
    
    
    ");
     80         for(int i=0; i<7; i++)
     81             for(int j=0; j<8; j++){
     82                 if(i==0 && j==0) continue;
     83                 scanf("%d",&g[i][j]);
     84             }
     85 
     86         printf("Layout #%d:
    
    ",++cas);
     87         for(int i=0; i<7; i++){
     88             for(int j=0; j<8; j++)
     89                 printf("%4d",g[i][j]);
     90             puts("");
     91         }
     92         puts("");
     93 
     94         printf("Maps resulting from layout #%d are:
    
    ",cas);
     95         dfs(0,0,0);
     96         printf("There are %d solution(s) for layout #%d.
    ",ans,cas);
     97     }
     98 
     99     return 0;
    100 }
  • 相关阅读:
    201671010109 《java程序联系》第十六周感想
    201671010109 《 java 程序设计》第十五周感想
    201671010109 《java程序设计》第十四周感想
    201671010109 《java程序设计》第十三周感想
    201671010109 《java程序设计》第十二周感想
    201671010109 《java程序设计》第十一周感想
    201671010109 2016-2017-2《java程序设计》第十周学习心得
    201671010109 2016-2017《java课程》第五周学习感想
    201971010109 2061-2017《java程序设计》第四周学习感想
    201671010107 2016-2017-2 《Java程序设计》总结
  • 原文地址:https://www.cnblogs.com/yxg123123/p/6827601.html
Copyright © 2020-2023  润新知