intさわだんのBlack History

刹那的レジェンドになりたい。

ICPC 国内予選2004B Red and Black AOJ1130

解法:幅優先探索やるだけ。queueの使い方を完全に忘れてて自分のブログを熟読して思い出した。

#include <bits/stdc++.h>
#define chmin(a, b) ((a)=min((a), (b)))
#define chmax(a, b) ((a)=max((a), (b)))
#define fs first
#define sc second
#define eb emplace_back
using namespace std;
 
typedef long long ll;
typedef pair<int, int> P;
typedef tuple<int, int, int> T;
 
const ll MOD=1e9+7;
const ll INF=1e18;
 
int dx[]={1, -1, 0, 0};
int dy[]={0, 0, 1, -1};

int check[25][25];

int main(){
    while(1){
        int w,h;
        cin >> w >> h;
        if(w == 0 && h == 0) break;
        char tile[23][23];
        queue<P> black;
        int ans = 0;
        for(int i = 0;i < h;i++){
            cin >> tile[i];
            for(int j = 0;j < w;j++){
                check[i][j] = 0;
                if(tile[i][j] == '@'){
                    black.push(P(i,j));
                }
            }
        }
        while(!black.empty()){
            P q = black.front(); black.pop();
            if(check[q.fs][q.sc] != 0) continue;
            ans++;
            check[q.fs][q.sc] = 1;
            for(int i = 0;i < 4;i++){
                int ni = q.fs+dx[i];
                int nj = q.sc+dy[i];
                if( min(ni,nj) >= 0 && ni < h && nj < w && check[ni][nj] == 0 && tile[ni][nj] == '.'){
                    black.push(P(ni,nj));
                }
            }
        }
        cout << ans << endl;
    }
}