Problem p01416 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <bits/stdc++.h>
typedef long long LL;
#define SORT(c) sort((c).begin(), (c).end())

#define FOR(i, a, b) for (int i = (a); i < (b); ++i)
#define REP(i, n) FOR(i, 0, n)

using namespace std;
int main(void) {
  int m, n;
  cin >> m >> n;
  vector<string> fi(m);
  REP(i, m) cin >> fi[i];
  int answer = 0;
  REP(i, m) REP(j, n) if (fi[i][j] == '.')-- answer;
  vector<pair<int, int>> pos[256];
  REP(i, m) REP(j, n) if (fi[i][j] != '.') {
    pos[fi[i][j]].push_back(make_pair(i, j));
  }
  bool flag = true;
  while (flag) {
    flag = false;
    FOR(i, 'A', 'Z' + 1) {
      if (pos[i].size() < 2)
        continue;
      int x0, x1, y0, y1;
      x0 = pos[i][0].first;
      y0 = pos[i][0].second;
      x1 = pos[i][1].first;
      y1 = pos[i][1].second;
      if (x0 == x1) {
        if (abs(y0 - y1) > 1) {
          bool er = true;
          if (y0 > y1)
            swap(y0, y1);
          FOR(j, y0 + 1, y1) if (fi[x0][j] != '.') er = false;
          if (er) {
            fi[x0][y0] = '.';
            fi[x1][y1] = '.';
            flag = true;
            pos[i].clear();
          }
        }
      } else if (y0 == y1) {
        if (abs(x0 - x1) > 1) {
          bool er = true;
          if (x0 > x1)
            swap(x0, x1);
          FOR(j, x0 + 1, x1) if (fi[j][y0] != '.') er = false;
          if (er) {
            fi[x0][y0] = '.';
            fi[x1][y1] = '.';
            flag = true;
            pos[i].clear();
          }
        }
      } else if ((x0 - x1) * (y0 - y1) > 0) {
        bool er0 = true, er1 = true;
        if (x0 > x1) {
          swap(x0, x1);
          swap(y0, y1);
        }
        FOR(j, x0 + 1, x1 + 1) if (fi[j][y0] != '.') er0 = false;
        FOR(j, y0 + 1, y1) if (fi[x1][j] != '.') er0 = false;
        FOR(j, y0 + 1, y1 + 1) if (fi[x0][j] != '.') er1 = false;
        FOR(j, x0 + 1, x1) if (fi[j][y1] != '.') er1 = false;
        if (er0 || er1) {
          fi[x0][y0] = '.';
          fi[x1][y1] = '.';
          flag = true;
          pos[i].clear();
        }
      } else if ((x0 - x1) * (y0 - y1) < 0) {
        bool er0 = true, er1 = true;
        if (x0 > x1) {
          swap(x0, x1);
          swap(y0, y1);
        }
        FOR(j, x0 + 1, x1 + 1) if (fi[j][y0] != '.') er0 = false;
        FOR(j, y1 + 1, y0) if (fi[x1][j] != '.') er0 = false;
        FOR(j, y1, y0) if (fi[x0][j] != '.') er1 = false;
        FOR(j, x0 + 1, x1) if (fi[j][y1] != '.') er1 = false;
        if (er0 || er1) {
          fi[x0][y0] = '.';
          fi[x1][y1] = '.';
          flag = true;
          pos[i].clear();
        }
      }
    }
  }
  REP(i, m) REP(j, n) if (fi[i][j] == '.')++ answer;
  cout << answer << endl;

  return 0;
}

Error: TLE

Fixed submission:

#include <bits/stdc++.h>
typedef long long LL;
#define SORT(c) sort((c).begin(), (c).end())

#define FOR(i, a, b) for (int i = (a); i < (b); ++i)
#define REP(i, n) FOR(i, 0, n)

using namespace std;
int main(void) {
  int m, n;
  cin >> m >> n;
  vector<string> fi(m);
  REP(i, m) cin >> fi[i];
  int answer = 0;
  REP(i, m) REP(j, n) if (fi[i][j] == '.')-- answer;
  vector<bool> exi(m, false), exj(n, false);
  REP(i, m) REP(j, n) if (fi[i][j] != '.') {
    exi[i] = true;
    exj[j] = true;
  }
  bool flag = true;
  while (flag) {
    REP(i, m) {
      REP(j, n) {
        if (!exi[i] && !exj[j])
          continue;
        if (fi[i][j] != '.')
          continue;
        vector<int> x, y;
        for (int k = i - 1; k >= 0; --k) {
          if (fi[k][j] != '.') {
            x.push_back(k);
            y.push_back(j);
            break;
          }
        }
        for (int k = i + 1; k < m; ++k) {
          if (fi[k][j] != '.') {
            x.push_back(k);
            y.push_back(j);
            break;
          }
        }
        for (int k = j - 1; k >= 0; --k) {
          if (fi[i][k] != '.') {
            x.push_back(i);
            y.push_back(k);
            break;
          }
        }
        for (int k = j + 1; k < n; ++k) {
          if (fi[i][k] != '.') {
            x.push_back(i);
            y.push_back(k);
            break;
          }
        }
        REP(k, x.size()) REP(l, k) {
          if (fi[x[k]][y[k]] == fi[x[l]][y[l]]) {
            fi[x[k]][y[k]] = '.';
            fi[x[l]][y[l]] = '.';
            flag = true;
          }
        }
      }
    }
  }
  REP(i, m) REP(j, n) if (fi[i][j] == '.')++ answer;
  cout << answer << endl;

  return 0;
}