[百练2816]红与黑(广搜)

题目描述:

总时间限制: 
1000ms 
内存限制: 
65536kB
描述
有一间长方形的房子,地上铺了红色、黑色两种颜色的正方形瓷砖。你站在其中一块黑色的瓷砖上,只能向相邻的黑色瓷砖移动。请写一个程序,计算你总共能够到达多少块黑色的瓷砖。
输入
包括多个数据集合。每个数据集合的第一行是两个整数W和H,分别表示x方向和y方向瓷砖的数量。W和H都不超过20。在接下来的H行中,每行包括W个字符。每个字符表示一块瓷砖的颜色,规则如下
1)‘.’:黑色的瓷砖;
2)‘#’:白色的瓷砖;
3)‘@’:黑色的瓷砖,并且你站在这块瓷砖上。该字符在每个数据集合中唯一出现一次。
当在一行中读入的是两个零时,表示输入结束。
输出
对每个数据集合,分别输出一行,显示你从初始位置出发能到达的瓷砖数(记数时包括初始位置的瓷砖)。
样例输入
6 9 
....#. 
.....# 
...... 
...... 
...... 
...... 
...... 
#@...# 
.#..#. 
0 0
样例输出
45
来源
1979



吐槽:说好的红呢,怎么成白了

思路:广搜,队列实现。出发点入队列,每次堆首点出队列,上下左右,不出界并且是黑色就标记走过了,然后入队列,计数加1。队列为空为止。

上代码

#include <iostream>
#include <queue>
using namespace std;
const int maxn=25;
int W, H;
int x, y;
int dx[4]={1, -1, 0, 0}, dy[4]={0, 0, 1, -1};
int count;
struct Map {
    int x, y;
    char c;
    bool gone;
}m[maxn][maxn];
void Scanf() {
    cin >> W >> H;
}
void Input() {
    for(int i=0; i<H; i++)
        for(int j=0; j<W; j++) {
            cin >> m[i][j].c;
            if(m[i][j].c=='@') {
                x=i;
                y=j;
            }
            m[i][j].x=i;
            m[i][j].y=j;

        }
}
void Init() {
    for(int i=0; i<maxn; i++)
        for(int j=0; j<maxn; j++)
            m[i][j].gone=false;
    count=1;
}
void Search() {
    queue<Map>Q;
    m[x][y].gone=true;
    Q.push(m[x][y]);
    while(!Q.empty()) {
        Map M=Q.front();
        Q.pop();
        for(int i=0; i<4; i++) {
            int X=M.x+dx[i];
            int Y=M.y+dy[i];
            if(X<0 || Y<0 || X>=H || Y>=W)
                continue;
            if(m[X][Y].c=='#' || m[X][Y].gone)
                continue;
            count++;
            m[X][Y].gone=true;
            Q.push(m[X][Y]);
        }
    }
}
void Print() {
    cout << count << endl;
}
int main() {
    Scanf();
    while(W!=0 && H!=0) {
        Input();
        Init();
        Search();
        Print();
        Scanf();
    }
    return 0;
}
已经AC了

猜你喜欢

转载自blog.csdn.net/pkuout/article/details/54925905