Problem p03157 (C++)

Buggy submission (status: Runtime Error):

#include <algorithm>
#include <cctype>
#include <cmath>
#include <cstdio>
#include <iomanip>
#include <iostream>
#include <map>
#include <math.h>
#include <queue>
#include <set>
#include <stack>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <utility>
#include <vector>

using namespace std;

#define ll long long
#define ld long double
#define EPS 0.0000000001
#define INF 1e9
#define LINF (ll) INF *INF
#define MOD 1000000007
#define rep(i, n) for (int i = 0; i < (n); i++)
#define loop(i, a, n) for (int i = a; i < (n); i++)
#define all(in) in.begin(), in.end()
#define shosu(x) fixed << setprecision(x)

#define int ll //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

typedef vector<int> vi;
typedef vector<string> vs;
typedef pair<int, int> pii;
typedef vector<pii> vp;

int gcd(int a, int b) {
  if (b == 0)
    return a;
  return gcd(b, a % b);
}
int lcm(int a, int b) { return a * b / gcd(a, b); }

int dx[] = {0, 1, 0, -1};
int dy[] = {1, 0, -1, 0};

signed main(void) {
  int i, j;
  int h, w;
  cin >> h >> w;
  vs s(h);
  rep(i, h) cin >> s[i];
  vector<vi> g(h * w);
  rep(i, h) rep(j, w) {
    rep(k, 4) {
      int nx = i + dx[k];
      int ny = j + dy[k];
      if (nx < 0 || nx >= h || ny < 0 || ny >= w)
        continue;
      if (s[i][j] == s[nx][ny])
        continue;
      g[i * w + j].push_back(nx * w + ny);
    }
  }
  /*
  rep(i,h*w){
      cout << i << endl;
      rep(j,g[i].size())cout << " " << g[i][j];cout << endl;
  }
  */
  vi used(h * w);
  int ans = 0;
  rep(i, h) rep(j, w) if (g[i * w + j].size() && s[i][j] == '#') {
    if (used[i * w + j] == 0) {
      int white = 0;
      int black = 0;
      queue<int> q;
      q.push(i * w + j);
      used[i * w + j]++;
      while (q.size()) {
        int now = q.front();
        q.pop();
        int x = now / h;
        int y = now % h;
        if (s[x][y] == '#')
          black++;
        else
          white++;
        rep(p, g[now].size()) {
          int ne = g[now][p];
          if (used[ne])
            continue;
          used[ne]++;
          q.push(ne);
        }
      }
      // cout << i << " " << j << " " << white << " " << black << endl;
      ans += white * black;
    }
  }
  cout << ans << endl;
}


Fixed submission:

#include <algorithm>
#include <cctype>
#include <cmath>
#include <cstdio>
#include <iomanip>
#include <iostream>
#include <map>
#include <math.h>
#include <queue>
#include <set>
#include <stack>
#include <stdlib.h>
#include <string.h>
#include <string>
#include <utility>
#include <vector>

using namespace std;

#define ll long long
#define ld long double
#define EPS 0.0000000001
#define INF 1e9
#define LINF (ll) INF *INF
#define MOD 1000000007
#define rep(i, n) for (int i = 0; i < (n); i++)
#define loop(i, a, n) for (int i = a; i < (n); i++)
#define all(in) in.begin(), in.end()
#define shosu(x) fixed << setprecision(x)

#define int ll //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!

typedef vector<int> vi;
typedef vector<string> vs;
typedef pair<int, int> pii;
typedef vector<pii> vp;

int gcd(int a, int b) {
  if (b == 0)
    return a;
  return gcd(b, a % b);
}
int lcm(int a, int b) { return a * b / gcd(a, b); }

int dx[] = {0, 1, 0, -1};
int dy[] = {1, 0, -1, 0};

signed main(void) {
  int i, j;
  int h, w;
  cin >> h >> w;
  vs s(h);
  rep(i, h) cin >> s[i];
  vector<vi> g(h * w);
  rep(i, h) rep(j, w) {
    rep(k, 4) {
      int nx = i + dx[k];
      int ny = j + dy[k];
      if (nx < 0 || nx >= h || ny < 0 || ny >= w)
        continue;
      if (s[i][j] == s[nx][ny])
        continue;
      g[i * w + j].push_back(nx * w + ny);
    }
  }
  /*
  rep(i,h*w){
      cout << i << endl;
      rep(j,g[i].size())cout << " " << g[i][j];cout << endl;
  }
  */
  vi used(h * w);
  int ans = 0;
  rep(i, h) rep(j, w) if (g[i * w + j].size() && s[i][j] == '#') {
    if (used[i * w + j] == 0) {
      int white = 0;
      int black = 0;
      queue<int> q;
      q.push(i * w + j);
      used[i * w + j]++;
      while (q.size()) {
        int now = q.front();
        q.pop();
        int x = now / w;
        int y = now % w;
        if (s[x][y] == '#')
          black++;
        else
          white++;
        rep(p, g[now].size()) {
          int ne = g[now][p];
          if (used[ne])
            continue;
          used[ne]++;
          q.push(ne);
        }
      }
      // cout << i << " " << j << " " << white << " " << black << endl;
      ans += white * black;
    }
  }
  cout << ans << endl;
}