1004 四子连棋

1004 四子连棋

 时间限制: 1 s
 空间限制: 128000 KB
 题目等级 : 黄金 Gold
 
 
题目描述 Description

在一个4*4的棋盘上摆放了14颗棋子,其中有7颗白色棋子,7颗黑色棋子,有两个空白地带,任何一颗黑白棋子都可以向上下左右四个方向移动到相邻的空格,这叫行棋一步,黑白双方交替走棋,任意一方可以先走,如果某个时刻使得任意一种颜色的棋子形成四个一线(包括斜线),这样的状态为目标棋局。

 
 

 

输入描述 Input Description
从文件中读入一个4*4的初始棋局,黑棋子用B表示,白棋子用W表示,空格地带用O表示。
输出描述 Output Description

用最少的步数移动到目标棋局的步数。

样例输入 Sample Input

BWBO
WBWB
BWBW
WBWO

样例输出 Sample Output

5

数据范围及提示 Data Size & Hint

hi

 1 #include<iostream>
 2 #include<cstring>
 3 #include<cstdio>
 4 using namespace std;
 5 int xx[5] = {0,0,0,1,-1};        //枚举四个方向 
 6 int yy[5] = {0,1,-1,0,0};
 7 int map[5][5],minn = 1000;        //利用数组代表“黑、白、空” minn代表所求的最小步数 
 8 char s;
 9 void Dfs(int x,int y,int num,int b)    //b表示 先走那种颜色 
10 {
11     int m = 100000,i,j,k;
12     if(num >= minn) 
13         return;                 //剪枝 如果已经比目前的最优解大了 就不用再Dfs了 
14     for(i = 1;i <= 4;i ++)        //4种目标棋局一一列举 如果有符合的 更新m的值 
15     {
16         if(map[i][1] == map[i][2] && map[i][2] == map[i][3] && map[i][3] == map[i][4] && (map[i][4] == 1 || map[i][4] == 2))//行相同更新 
17         m = num;
18         if(map[1][i] == map[2][i] && map[2][i] == map[3][i] && map[3][i] == map[4][i] && (map[4][i] == 1 || map[4][i] == 2))//列相同更新 
19         m = num;
20     }
21     if(map[1][1] == map[2][2] && map[2][2] == map[3][3] && map[3][3] == map[4][4] && (map[4][4]==1 || map[4][4] == 2))//左上到右下相同更新 
22         m = num;
23     if(map[4][1] == map[3][2] && map[3][2] == map[2][3] && map[2][3] == map[1][4] && (map[1][4]==1 || map[1][4] == 2))//右上到左下相同更新 
24         m = num;
25     if(m < minn)            //m在上面已经更新为当前接了 这里用m更新minn 
26     {
27         minn = m;
28         return;                //不用往后搜索了 因为后面不如现在优 
29     }
30     for(i = 1;i <= 4;i ++)
31     {
32         int tx = x + xx[i];        //横坐标更新
33         int ty = y + yy[i];        //纵坐标更新
34         if(tx > 0 && tx <= 4 && ty > 0 && ty <= 4 && map[tx][ty] == b)        //边界判断 
35         {
36             map[x][y] = map[tx][ty];
37             map[tx][ty] = 0;        //走完之后map[tx][ty]变空  map[x][y]变map[tx][ty]
38             if(b == 1)
39             b = 2;                //黑白交替走 上次走黑 下次走白 
40             else b = 1;
41             for(j = 1;j <= 4;j ++)        //因为空格又不止一个 所以 找空格 
42             for(k = 1;k <= 4;k ++)
43             if(!map[j][k])        //空格的值为0 
44                 Dfs(j,k,num+1,b);
45             map[tx][ty] = map[x][y];        //回溯 
46             map[x][y] = 0;
47             if(b == 1)  b = 2;
48             else    b = 1;
49         }
50     }
51 }
52 int main()
53 {
54     int i,j;
55     for(i = 1;i <= 4;i ++)
56     for(j = 1;j <= 4;j ++)
57     {
58         cin >> s;
59         if(s == 'W') map[i][j] = 1;        //白棋 
60         if(s == 'B') map[i][j] = 2;        //黑棋 
61     }
62     for(i = 1;i <= 4;i ++)
63     for(j = 1;j <= 4;j ++)
64     if(!map[i][j])        //空格 
65     {
66         Dfs(i,j,0,1);        //先走白棋 
67         Dfs(i,j,0,2);        //先走黑棋 
68     }
69     cout<<minn<<endl;
70     return 0;
71 }

 

posted @ 2017-04-22 20:43  MJT12044  阅读(157)  评论(0编辑  收藏  举报