Problem p03718 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
using namespace std;

#ifdef SG
#include <debug.h>
#else
template <typename T> struct outputer;
struct outputable {};
#define PRINT(...)
#define OUTPUT(...)
#define show(...)
#define debug(...)
#define deepen(...)
#define timer(...)
#define fbegin(...)
#define fend
#define pbegin(...)
#define pend
#endif

#define ARG4(_1, _2, _3, _4, ...) _4

#define forn3(i, l, r) for (int i = int(l); i < int(r); ++i)
#define forn2(i, n) forn3(i, 0, n)
#define forn(...) ARG4(__VA_ARGS__, forn3, forn2)(__VA_ARGS__)

#define ford3(i, l, r) for (int i = int(r) - 1; i >= int(l); --i)
#define ford2(i, n) ford3(i, 0, n)
#define ford(...) ARG4(__VA_ARGS__, ford3, ford2)(__VA_ARGS__)

#define ve vector
#define pa pair
#define tu tuple
#define mp make_pair
#define mt make_tuple
#define pb emplace_back
#define fs first
#define sc second
#define all(a) (a).begin(), (a).end()
#define sz(a) ((int)(a).size())

typedef long double ld;
typedef int64_t ll;
typedef uint64_t ull;
typedef uint32_t ui;
typedef uint16_t us;
typedef uint8_t uc;
typedef pa<int, int> pii;
typedef pa<int, ll> pil;
typedef pa<ll, int> pli;
typedef pa<ll, ll> pll;
typedef ve<int> vi;

template <typename T> inline auto sqr(T x) -> decltype(x * x) { return x * x; }
template <typename T1, typename T2> inline bool umx(T1 &a, T2 b) {
  if (a < b) {
    a = b;
    return 1;
  }
  return 0;
}
template <typename T1, typename T2> inline bool umn(T1 &a, T2 b) {
  if (b < a) {
    a = b;
    return 1;
  }
  return 0;
}

const int N = 100;

struct Input {
  int n, m;
  string s[N];

  bool read() {
    if (!(cin >> n >> m)) {
      return 0;
    }
    getline(cin, s[0]);
    forn(i, n) { getline(cin, s[i]); }
    return 1;
  }

  void init(const Input &input) { *this = input; }
};

struct Data : Input {
  int ans;

  void write() { cout << ans << endl; }
};

namespace Main {
const int V = N + 10;
const int E = V * V;
const int inf = 500000000;

struct Solution : Data {
  struct edge {
    int to;
    int b, f;

    edge(int to_ = -1, int b_ = 0) : to(to_), b(b_), f(0) {}

    int r() { return b - f; }
  };

  int es = 0;
  edge e[2 * E];

  void push(int num, int d) {
    e[num].f += d;
    e[num ^ 1].f -= d;
  }

  vi adj[V];

  void add_edge(int x, int y, int b) {
    e[es] = edge(y, b);
    adj[x].pb(es);
    ++es;
    e[es] = edge(x, b);
    adj[y].pb(es);
    ++es;
  }

  int st, fn;

  int l[V];

  bool bfs() {
    memset(l, -1, sizeof l);
    vi q(1, st);
    l[st] = 0;
    forn(i, sz(q)) {
      int v = q[i];
      for (auto j : adj[v]) {
        int to = e[j].to;
        if (l[to] == -1 && e[j].r()) {
          q.pb(to);
          l[to] = l[v] + 1;
        }
      }
    }
    return l[fn] != -1;
  }

  int done[V];

  int dfs(int v, int r) {
    if (v == fn) {
      return r;
    }
    for (; done[v] < sz(adj[v]); ++done[v]) {
      int i = adj[v][done[v]];
      int to = e[i].to;
      if (l[to] != l[v] + 1 || !e[i].r()) {
        continue;
      }
      int d = dfs(to, min(r, e[i].r()));
      if (d) {
        push(i, d);
        return d;
      }
    }
    return 0;
  }

  int dinic() {
    int res = 0;
    while (1) {
      if (!bfs()) {
        break;
      }
      memset(done, 0, sizeof done);
      while (int d = dfs(st, inf)) {
        res += d;
      }
    }
    return res;
  }

  void solve() {
    st = n + m;
    fn = n + m + 1;

    es = 0;
    forn(i, n) {
      forn(j, m) {
        if (s[i][j] == 'o') {
          add_edge(i, j + n, 1);
        }
        if (s[i][j] == 'S') {
          add_edge(st, i, inf);
          add_edge(st, j + n, inf);
        }
        if (s[i][j] == 'T') {
          add_edge(i, fn, inf);
          add_edge(j + n, fn, inf);
        }
      }
    }
    ans = dinic();
    if (ans >= inf) {
      ans = -1;
    }
  }

  void clear() { *this = Solution(); }
};
} // namespace Main

Main::Solution sol;

int main() {
  cout.setf(ios::showpoint | ios::fixed);
  cout.precision(20);

#ifdef SG
  freopen((problemname + ".in").c_str(), "r", stdin);
  //		freopen((problemname + ".out").c_str(), "w", stdout);
  while (sol.read()) {
    sol.solve();
    sol.write();
    sol.clear();
  }
#else
  sol.read();
  sol.solve();
  sol.write();
#endif

  /*
  int t;
  cin >> t;
  forn (i, t) {
          sol.read();
          sol.solve();
          sol.write();
          sol.clear();
  }
  */

  return 0;
}


Fixed submission:
#include <bits/stdc++.h>
using namespace std;

#ifdef SG
#include <debug.h>
#else
template <typename T> struct outputer;
struct outputable {};
#define PRINT(...)
#define OUTPUT(...)
#define show(...)
#define debug(...)
#define deepen(...)
#define timer(...)
#define fbegin(...)
#define fend
#define pbegin(...)
#define pend
#endif

#define ARG4(_1, _2, _3, _4, ...) _4

#define forn3(i, l, r) for (int i = int(l); i < int(r); ++i)
#define forn2(i, n) forn3(i, 0, n)
#define forn(...) ARG4(__VA_ARGS__, forn3, forn2)(__VA_ARGS__)

#define ford3(i, l, r) for (int i = int(r) - 1; i >= int(l); --i)
#define ford2(i, n) ford3(i, 0, n)
#define ford(...) ARG4(__VA_ARGS__, ford3, ford2)(__VA_ARGS__)

#define ve vector
#define pa pair
#define tu tuple
#define mp make_pair
#define mt make_tuple
#define pb emplace_back
#define fs first
#define sc second
#define all(a) (a).begin(), (a).end()
#define sz(a) ((int)(a).size())

typedef long double ld;
typedef int64_t ll;
typedef uint64_t ull;
typedef uint32_t ui;
typedef uint16_t us;
typedef uint8_t uc;
typedef pa<int, int> pii;
typedef pa<int, ll> pil;
typedef pa<ll, int> pli;
typedef pa<ll, ll> pll;
typedef ve<int> vi;

template <typename T> inline auto sqr(T x) -> decltype(x * x) { return x * x; }
template <typename T1, typename T2> inline bool umx(T1 &a, T2 b) {
  if (a < b) {
    a = b;
    return 1;
  }
  return 0;
}
template <typename T1, typename T2> inline bool umn(T1 &a, T2 b) {
  if (b < a) {
    a = b;
    return 1;
  }
  return 0;
}

const int N = 100;

struct Input {
  int n, m;
  string s[N];

  bool read() {
    if (!(cin >> n >> m)) {
      return 0;
    }
    getline(cin, s[0]);
    forn(i, n) { getline(cin, s[i]); }
    return 1;
  }

  void init(const Input &input) { *this = input; }
};

struct Data : Input {
  int ans;

  void write() { cout << ans << endl; }
};

namespace Main {
const int V = 2 * N + 10;
const int E = N * N + 10 * N;
const int inf = 500000000;

struct Solution : Data {
  struct edge {
    int to;
    int b, f;

    edge(int to_ = -1, int b_ = 0) : to(to_), b(b_), f(0) {}

    int r() { return b - f; }
  };

  int es = 0;
  edge e[2 * E];

  void push(int num, int d) {
    e[num].f += d;
    e[num ^ 1].f -= d;
  }

  vi adj[V];

  void add_edge(int x, int y, int b) {
    e[es] = edge(y, b);
    adj[x].pb(es);
    ++es;
    e[es] = edge(x, b);
    adj[y].pb(es);
    ++es;
  }

  int st, fn;

  int l[V];

  bool bfs() {
    memset(l, -1, sizeof l);
    vi q(1, st);
    l[st] = 0;
    forn(i, sz(q)) {
      int v = q[i];
      for (auto j : adj[v]) {
        int to = e[j].to;
        if (l[to] == -1 && e[j].r()) {
          q.pb(to);
          l[to] = l[v] + 1;
        }
      }
    }
    return l[fn] != -1;
  }

  int done[V];

  int dfs(int v, int r) {
    if (v == fn) {
      return r;
    }
    for (; done[v] < sz(adj[v]); ++done[v]) {
      int i = adj[v][done[v]];
      int to = e[i].to;
      if (l[to] != l[v] + 1 || !e[i].r()) {
        continue;
      }
      int d = dfs(to, min(r, e[i].r()));
      if (d) {
        push(i, d);
        return d;
      }
    }
    return 0;
  }

  int dinic() {
    int res = 0;
    while (1) {
      if (!bfs()) {
        break;
      }
      memset(done, 0, sizeof done);
      while (int d = dfs(st, inf)) {
        res += d;
      }
    }
    return res;
  }

  void solve() {
    st = n + m;
    fn = n + m + 1;

    es = 0;
    forn(i, n) {
      forn(j, m) {
        if (s[i][j] == 'o') {
          add_edge(i, j + n, 1);
        }
        if (s[i][j] == 'S') {
          add_edge(st, i, inf);
          add_edge(st, j + n, inf);
        }
        if (s[i][j] == 'T') {
          add_edge(i, fn, inf);
          add_edge(j + n, fn, inf);
        }
      }
    }
    ans = dinic();
    if (ans >= inf) {
      ans = -1;
    }
  }

  void clear() { *this = Solution(); }
};
} // namespace Main

Main::Solution sol;

int main() {
  cout.setf(ios::showpoint | ios::fixed);
  cout.precision(20);

#ifdef SG
  freopen((problemname + ".in").c_str(), "r", stdin);
  //		freopen((problemname + ".out").c_str(), "w", stdout);
  while (sol.read()) {
    sol.solve();
    sol.write();
    sol.clear();
  }
#else
  sol.read();
  sol.solve();
  sol.write();
#endif

  /*
  int t;
  cin >> t;
  forn (i, t) {
          sol.read();
          sol.solve();
          sol.write();
          sol.clear();
  }
  */

  return 0;
}