Problem p01421 (C++) — buggy submission, verdict: Runtime Error

#include <algorithm>
#include <array>
#include <assert.h>
#include <bitset>
#include <complex>
#include <functional>
#include <iomanip>
#include <iostream>
#include <limits>
#include <map>
#include <math.h>
#include <numeric>
#include <queue>
#include <set>
#include <stack>
#include <stdio.h>
#include <stdio.h>
#include <string.h>
#include <string>
#include <vector>
using namespace std;
template <class BidirectionalIterator>
bool next_combination(BidirectionalIterator first1, BidirectionalIterator last1,
                      BidirectionalIterator first2,
                      BidirectionalIterator last2) {
  if ((first1 == last1) || (first2 == last2)) {
    return false;
  }
  BidirectionalIterator m1 = last1;
  BidirectionalIterator m2 = last2;
  --m2;
  while (--m1 != first1 && !(*m1 < *m2)) {
  }
  bool result = (m1 == first1) && !(*first1 < *m2);
  if (!result) {
    // ?
    while (first2 != m2 && !(*m1 < *first2)) {
      ++first2;
    }
    first1 = m1;
    std::iter_swap(first1, first2);
    ++first1;
    ++first2;
  }
  if ((first1 != last1) && (first2 != last2)) {
    // ?
    m1 = last1;
    m2 = first2;
    while ((m1 != first1) && (m2 != last2)) {
      std::iter_swap(--m1, m2);
      ++m2;
    }
    // ?
    std::reverse(first1, m1);
    std::reverse(first1, last1);
    std::reverse(m2, last2);
    std::reverse(first2, last2);
  }
  return !result;
}

template <class BidirectionalIterator>
bool next_combination(BidirectionalIterator first, BidirectionalIterator middle,
                      BidirectionalIterator last) {
  return next_combination(first, middle, middle, last);
}

struct tumiki {
  long long int x;
  long long int y;
  long long int id;
};

class Compare {
public:
  bool operator()(const pair<int, long long int> &l,
                  const pair<int, long long int> &r) {
    return l.second > r.second;
  }
};

struct island {
  int id;
  int sink;
  vector<pair<int, int>> edges;
  island(int N) : edges(N) {}
};

#define _GLIBCXX_DEBUG
#include <iostream>
#include <vector>

using namespace std;

#define REP(i, n) for (int i = 0; i < (int)n; ++i)
#define FOR(i, c) for (auto i = (c).begin(); i != (c).end(); ++i)
#define ALL(c) (c).begin(), (c).end()

const int INF = 2147483647;

typedef int Weight;
struct Edge {
  int id;
  bool real;
  int src, dst;
  Weight weight;
  Edge(bool real, int id, int src, int dst, Weight weight)
      : id(id), real(real), src(src), dst(dst), weight(weight) {}
};
bool operator<(const Edge &e, const Edge &f) {
  return e.weight != f.weight ? e.weight > f.weight : // !!INVERSE!!
             e.src != f.src ? e.src < f.src
                            : e.dst < f.dst;
}
typedef vector<Edge> Edges;
typedef vector<Edges> Graph;

typedef vector<Weight> Array;
typedef vector<Array> Matrix;
#define RESIDUE(s, t) (capacity[s][t] - flow[s][t])

vector<pair<int, int>> uses;

// 流量0の逆辺も張らないと正しく求まらないので注意
Weight maximumFlow(const Graph &g, int s, int t) {
  int n = g.size();
  Matrix flow(n, Array(n)), capacity(n, Array(n));
  REP(u, n) FOR(e, g[u]) capacity[e->src][e->dst] += e->weight;

  Weight total = 0;
  while (1) {
    queue<int> Q;
    Q.push(s);
    vector<int> prev(n, -1);
    prev[s] = s;
    while (!Q.empty() && prev[t] < 0) {
      int u = Q.front();
      Q.pop();
      FOR(e, g[u]) if (prev[e->dst] < 0 && RESIDUE(u, e->dst) > 0) {
        prev[e->dst] = u;
        Q.push(e->dst);
      }
    }
    int now = t;
    while (prev[now] != now && prev[now] != -1) {
      uses.push_back({prev[now], now});
      now = prev[now];
    }
    if (prev[t] < 0)
      return total; // prev[x] == -1 <=> t-side
    Weight inc = INF;
    for (int j = t; prev[j] != j; j = prev[j])
      inc = min(inc, RESIDUE(prev[j], j));
    for (int j = t; prev[j] != j; j = prev[j])
      flow[prev[j]][j] += inc, flow[j][prev[j]] -= inc;
    total += inc;
  }
}

int main() {
  int N, M;
  cin >> N >> M;
  Graph g(N);

  for (int i = 0; i < M; ++i) {
    int x, y;
    cin >> x >> y;
    x--;
    y--;
    g[x].push_back(Edge(true, i, x, y, 1));
    g[y].push_back(Edge(false, i, y, x, 1));
  }
  int S, T;
  cin >> S >> T;
  S--;
  T--;
  int ans = maximumFlow(g, S, T);

  vector<int> changes(M, 1);
  for (int i = 0; i < uses.size(); ++i) {
    for (int j = 0; j < g[uses[i].first].size(); ++j) {
      if (g[uses[i].first][j].dst == uses[i].second) {
        if (g[uses[i].first][j].real) {
          changes[g[uses[i].first][j].id]++;
        } else {
          changes[g[uses[i].first][j].id]--;
        }
      }
    }
  }
  vector<int> cs;
  for (int i = 0; i < M; ++i) {
    if (changes[i] == 0) {
      cs.push_back(i + 1);
    }
  }
  cout << ans << endl << cs.size() << endl;
  for (int i = 0; i < cs.size(); ++i) {
    cout << cs[i] << endl;
  }
  return 0;
}

Error: 0

Fixed submission:

#include <algorithm>
#include <array>
#include <assert.h>
#include <bitset>
#include <complex>
#include <functional>
#include <iomanip>
#include <iostream>
#include <limits>
#include <map>
#include <math.h>
#include <numeric>
#include <queue>
#include <set>
#include <stack>
#include <stdio.h>
#include <stdio.h>
#include <string.h>
#include <string>
#include <vector>
using namespace std;
template <class BidirectionalIterator>
bool next_combination(BidirectionalIterator first1, BidirectionalIterator last1,
                      BidirectionalIterator first2,
                      BidirectionalIterator last2) {
  if ((first1 == last1) || (first2 == last2)) {
    return false;
  }
  BidirectionalIterator m1 = last1;
  BidirectionalIterator m2 = last2;
  --m2;
  while (--m1 != first1 && !(*m1 < *m2)) {
  }
  bool result = (m1 == first1) && !(*first1 < *m2);
  if (!result) {
    // ?
    while (first2 != m2 && !(*m1 < *first2)) {
      ++first2;
    }
    first1 = m1;
    std::iter_swap(first1, first2);
    ++first1;
    ++first2;
  }
  if ((first1 != last1) && (first2 != last2)) {
    // ?
    m1 = last1;
    m2 = first2;
    while ((m1 != first1) && (m2 != last2)) {
      std::iter_swap(--m1, m2);
      ++m2;
    }
    // ?
    std::reverse(first1, m1);
    std::reverse(first1, last1);
    std::reverse(m2, last2);
    std::reverse(first2, last2);
  }
  return !result;
}

template <class BidirectionalIterator>
bool next_combination(BidirectionalIterator first, BidirectionalIterator middle,
                      BidirectionalIterator last) {
  return next_combination(first, middle, middle, last);
}

struct tumiki {
  long long int x;
  long long int y;
  long long int id;
};

class Compare {
public:
  bool operator()(const pair<int, long long int> &l,
                  const pair<int, long long int> &r) {
    return l.second > r.second;
  }
};

struct island {
  int id;
  int sink;
  vector<pair<int, int>> edges;
  island(int N) : edges(N) {}
};

#define _GLIBCXX_DEBUG
#include <iostream>
#include <vector>

using namespace std;

#define REP(i, n) for (int i = 0; i < (int)n; ++i)
#define FOR(i, c) for (auto i = (c).begin(); i != (c).end(); ++i)
#define ALL(c) (c).begin(), (c).end()

const int INF = 2147483647;

typedef int Weight;
struct Edge {
  int id;
  bool real;
  int src, dst;
  Weight weight;
  Edge(bool real, int id, int src, int dst, Weight weight)
      : id(id), real(real), src(src), dst(dst), weight(weight) {}
};
bool operator<(const Edge &e, const Edge &f) {
  return e.weight != f.weight ? e.weight > f.weight : // !!INVERSE!!
             e.src != f.src ? e.src < f.src
                            : e.dst < f.dst;
}
typedef vector<Edge> Edges;
typedef vector<Edges> Graph;

typedef vector<Weight> Array;
typedef vector<Array> Matrix;
#define RESIDUE(s, t) (capacity[s][t] - flow[s][t])

vector<pair<int, int>> uses;

// 流量0の逆辺も張らないと正しく求まらないので注意
Weight maximumFlow(const Graph &g, int s, int t) {
  int n = g.size();
  Matrix flow(n, Array(n)), capacity(n, Array(n));
  REP(u, n) FOR(e, g[u]) capacity[e->src][e->dst] += e->weight;

  Weight total = 0;
  while (1) {
    queue<int> Q;
    Q.push(s);
    vector<int> prev(n, -1);
    prev[s] = s;
    while (!Q.empty() && prev[t] < 0) {
      int u = Q.front();
      Q.pop();
      FOR(e, g[u]) if (prev[e->dst] < 0 && RESIDUE(u, e->dst) > 0) {
        prev[e->dst] = u;
        Q.push(e->dst);
      }
    }
    int now = t;
    while (prev[now] != now && prev[now] != -1) {
      uses.push_back({prev[now], now});
      now = prev[now];
    }
    if (prev[t] < 0)
      return total; // prev[x] == -1 <=> t-side
    Weight inc = INF;
    for (int j = t; prev[j] != j; j = prev[j])
      inc = min(inc, RESIDUE(prev[j], j));
    for (int j = t; prev[j] != j; j = prev[j])
      flow[prev[j]][j] += inc, flow[j][prev[j]] -= inc;
    total += inc;
  }
}

int main() {
  int N, M;
  cin >> N >> M;
  Graph g(N);

  for (int i = 0; i < M; ++i) {
    int x, y;
    cin >> x >> y;
    x--;
    y--;
    g[x].push_back(Edge(true, i, x, y, 1));
    g[y].push_back(Edge(false, i, y, x, 1));
  }
  int S, T;
  cin >> S >> T;
  S--;
  T--;
  int ans = maximumFlow(g, S, T);

  vector<int> changes(N, 1);
  for (int i = 0; i < uses.size(); ++i) {
    for (int j = 0; j < g[uses[i].first].size(); ++j) {
      if (g[uses[i].first][j].dst == uses[i].second) {
        if (g[uses[i].first][j].real) {
          changes[g[uses[i].first][j].id]++;
        } else {
          changes[g[uses[i].first][j].id]--;
        }
      }
    }
  }
  vector<int> cs;
  for (int i = 0; i < N; ++i) {
    if (changes[i] == 0) {
      cs.push_back(i + 1);
    }
  }
  cout << ans << endl << cs.size() << endl;
  for (int i = 0; i < cs.size(); ++i) {
    cout << cs[i] << endl;
  }
  return 0;
}