[HDOJ1175]连连看

 

原题链接:http://acm.hdu.edu.cn/showproblem.php?pid=1175

连连看

Time Limit: 20000/10000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 23190    Accepted Submission(s): 5718

Problem Description
“连连看”相信很多人都玩过。没玩过也没关系,下面我给大家介绍一下游戏规则:在一个棋盘中,放了很多的棋子。如果某两个相同的棋子,可以通过一条线连起来(这条线不能经过其它棋子),而且线的转折次数不超过两次,那么这两个棋子就可以在棋盘上消去。不好意思,由于我以前没有玩过连连看,咨询了同学的意见,连线不能从外面绕过去的,但事实上这是错的。现在已经酿成大祸,就只能将错就错了,连线不能从外围绕过。
玩家鼠标先后点击两块棋子,试图将他们消去,然后游戏的后台判断这两个方格能不能消去。现在你的任务就是写这个后台程序。

  

Input
输入数据有多组。每组数据的第一行有两个正整数n,m(0<n<=1000,0<m<1000),分别表示棋盘的行数与列数。在接下来的n行中,每行有m个非负整数描述棋盘的方格分布。0表示这个位置没有棋子,正整数表示棋子的类型。接下来的一行是一个正整数q(0<q<50),表示下面有q次询问。在接下来的q行里,每行有四个正整数x1,y1,x2,y2,表示询问第x1行y1列的棋子与第x2行y2列的棋子能不能消去。n=0,m=0时,输入结束。
注意:询问之间无先后关系,都是针对当前状态的!

  

  

Output
每一组输入数据对应一行输出。如果能消去则输出"YES",不能则输出"NO"。

  

  

Sample Input
3 4 1 2 3 4 0 0 0 0 4 3 2 1 4 1 1 3 4 1 1 2 4 1 1 3 3 2 1 2 4 3 4 0 1 4 3 0 2 4 1 0 0 0 0 2 1 1 2 4 1 3 2 3 0 0
 

  

Sample Output
YES NO NO NO NO YES
 
 
之前用DFS写了一次,内存超了。于是用BFS重写了一次。
 
注意满足条件的判断,这个稍微有一点复杂。应该有初始情况两个数不相等的情况。

注意题目要求“线的转折次数不超过两次”,我没有算转折点,我算的折线数目。(≤3)

  1 #include <stdio.h>
  2 #include <string.h>
  3 #include <queue>
  4 #include <iostream>
  5 using namespace std;
  6 int n, m, s;
  7 int map[1002][1002];
  8 int vis[1002][1002];
  9 int x1, y1, x2, y2;
 10 int dir[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
 11 typedef struct Position
 12 {
 13     int x, y;
 14     int count;
 15 }Position;
 16 
 17 int BFS()
 18 {
 19     queue<Position> q;
 20     Position fst, tmp;
 21     fst.x = x1;
 22     fst.y = y1;
 23     fst.count = -1; //init. first one not calculate.
 24     q.push(fst);
 25     vis[x1][y1] = 0;
 26     int sum;
 27     while(!q.empty())
 28     {   
 29         fst = q.front();
 30         q.pop();
 31         for(int i = 0; i < 4; i++)
 32         {
 33             tmp.x = fst.x + dir[i][0];
 34             tmp.y = fst.y + dir[i][1];
 35             if(fst.count == i)
 36             {
 37                 sum = vis[fst.x][fst.y];
 38             }
 39             else
 40             {
 41                 sum = vis[fst.x][fst.y] + 1;
 42             }
 43             tmp.count = i;
 44             if( tmp.x >= 0 && 
 45                 tmp.x < n  &&
 46                 tmp.y >= 0 && 
 47                 tmp.y < m  &&
 48               (vis[tmp.x][tmp.y] == 0 || sum <= vis[tmp.x][tmp.y]))
 49             { 
 50                vis[tmp.x][tmp.y] = sum; 
 51                if(tmp.x == x2 && tmp.y == y2)
 52                 {   
 53                     if(vis[tmp.x][tmp.y] <= 3)
 54                     {
 55                         return 1;
 56                     }
 57                 }
 58                 if(vis[tmp.x][tmp.y] > 3)
 59                 {
 60                     continue;
 61                 }
 62                 if(map[tmp.x][tmp.y] == 0)
 63                 {
 64                     q.push(tmp);
 65                 }
 66             }
 67         }
 68     }
 69     return 0;
 70 }
 71     
 72     
 73 int main()
 74 {   
 75     while(scanf("%d%d",&n,&m) != EOF && n+m)
 76     {   
 77         for(int i = 0; i < n; i++)
 78         {
 79             for(int j = 0; j < m; j++)
 80             {    
 81                 scanf("%d", &map[i][j]);
 82             }
 83         }
 84         scanf("%d", &s);
 85         for(int i = 0 ; i < s; i++)
 86         {
 87             scanf("%d %d %d %d", &x1, &y1, &x2, &y2);
 88             x1--;
 89             x2--;
 90             y1--;
 91             y2--;
 92             if((map[x1][y1] != map[x2][y2]) ||
 93                 map[x1][y1] == 0 ||
 94                 map[x2][y2] == 0 ||
 95                 (x1==x2&&y1==y2))
 96             {
 97                 printf("NO
");
 98                 continue;
 99             }
100             memset(vis, 0, sizeof(vis));
101             if(BFS())
102             {
103                 printf("YES
");
104             }
105             else
106             {
107                 printf("NO
");
108             }
109         }
110       
111     }
112     return 0;
113 }
View Code
原文地址:https://www.cnblogs.com/kirai/p/4517091.html