Problem p02942 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>

#include <queue>
#include <vector>

using namespace std;

const int N = 210, M = 20010;

const int INF = 1e9;

struct edge {
  int from, to, flow, cap;
  edge() {}
  edge(int _1, int _2, int _3, int _4) : from(_1), to(_2), flow(_3), cap(_4) {}
};

struct Dinic {
  edge edges[M];
  int head[N], nxt[M], tot;

  inline void init() {
    memset(head, -1, sizeof(head));
    tot = 0;
  }

  inline void add_edge(int x, int y, int z) {
    edges[tot] = edge(x, y, 0, z);
    nxt[tot] = head[x];
    head[x] = tot++;
    edges[tot] = edge(y, x, 0, 0);
    nxt[tot] = head[y];
    head[y] = tot++;
  }

  int s, t, L, R;

  int cur[N];

  int d[N];

  bool bfs() {
    memset(d + L, -1, sizeof(int) * (R - L + 1));

    queue<int> q;
    q.push(s);
    d[s] = 0;

    while (!q.empty()) {
      int x = q.front();
      q.pop();
      cur[x] = head[x];
      for (int i = head[x]; ~i; i = nxt[i]) {
        edge &e = edges[i];
        if (d[e.to] == -1 && e.flow < e.cap) {
          d[e.to] = d[x] + 1;
          q.push(e.to);
        }
      }
    }

    return d[t] != -1;
  }

  int dfs(int x, int a) {
    if (x == t || a == 0)
      return a;

    int flow = 0, f = 0;
    for (int &i = cur[x]; ~i; i = nxt[i]) {
      edge &e = edges[i];
      if (d[e.to] == d[x] + 1 && (f = dfs(e.to, min(a, e.cap - e.flow))) > 0) {
        e.flow += f;
        edges[i ^ 1].flow -= f;
        a -= f;
        flow += f;
        if (!a)
          break;
      }
    }

    return flow;
  }

  inline int maxflow(int s, int t) {
    this->s = s;
    this->t = t;
    int flow = 0;
    while (bfs())
      flow += dfs(s, INF);
    return flow;
  }
} dinic;

int n, m;

int a[110][110], b[110][110], c[110][110];
int val[110][110];

vector<int> vec[110][110];

inline int get(int x) { return (x - 1) / m + 1; }

int main() {
  cin >> n >> m;

  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++)
      scanf("%d", &a[i][j]);

  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++)
      vec[i][get(a[i][j])].push_back(a[i][j]);

  for (int i = 1; i <= m; i++) {
    dinic.init();

    dinic.L = 0, dinic.R = 2 * n + 2;
    int S = 2 * n + 1, T = 2 * n + 2;

    for (int j = 1; j <= n; j++)
      dinic.add_edge(S, j, 1);
    for (int j = 1; j <= n; j++)
      dinic.add_edge(j + n, T, 1);
    for (int j = 1; j <= n; j++)
      for (int k = 1; k <= n; k++)
        if (!vec[j][k].empty())
          dinic.add_edge(j, k + n, 1);
    dinic.maxflow(S, T);
    for (int j = 1; j <= n; j++)
      for (int k = dinic.head[j]; ~k; k = dinic.nxt[k]) {
        edge &e = dinic.edges[k];
        if (e.to != S && e.to != T && e.to > n && e.cap == e.flow) {
          b[j][i] = vec[j][e.to - n].back();
          vec[j][e.to - n].pop_back();
        }
      }
  }

  for (int i = 1; i <= m; i++) {
    static int tmp[110];
    for (int j = 1; j <= n; j++)
      tmp[j] = b[j][i];
    sort(tmp + 1, tmp + 1 + n, [](int a, int b) { return get(a) < get(b); });
    for (int j = 1; j <= n; j++)
      c[j][i] = tmp[j];
  }

  for (int i = 1; i <= n; i++, puts(""))
    for (int j = 1; j <= m; j++)
      printf("%d ", b[i][j]);
  for (int i = 1; i <= n; i++, puts(""))
    for (int j = 1; j <= m; j++)
      printf("%d ", c[i][j]);

  return 0;
}

Fixed submission:
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>

#include <queue>
#include <vector>

using namespace std;

const int N = 210, M = 40010;

const int INF = 1e9;

struct edge {
  int from, to, flow, cap;
  edge() {}
  edge(int _1, int _2, int _3, int _4) : from(_1), to(_2), flow(_3), cap(_4) {}
};

struct Dinic {
  edge edges[M];
  int head[N], nxt[M], tot;

  inline void init() {
    memset(head, -1, sizeof(head));
    tot = 0;
  }

  inline void add_edge(int x, int y, int z) {
    edges[tot] = edge(x, y, 0, z);
    nxt[tot] = head[x];
    head[x] = tot++;
    edges[tot] = edge(y, x, 0, 0);
    nxt[tot] = head[y];
    head[y] = tot++;
  }

  int s, t, L, R;

  int cur[N];

  int d[N];

  bool bfs() {
    memset(d + L, -1, sizeof(int) * (R - L + 1));

    queue<int> q;
    q.push(s);
    d[s] = 0;

    while (!q.empty()) {
      int x = q.front();
      q.pop();
      cur[x] = head[x];
      for (int i = head[x]; ~i; i = nxt[i]) {
        edge &e = edges[i];
        if (d[e.to] == -1 && e.flow < e.cap) {
          d[e.to] = d[x] + 1;
          q.push(e.to);
        }
      }
    }

    return d[t] != -1;
  }

  int dfs(int x, int a) {
    if (x == t || a == 0)
      return a;

    int flow = 0, f = 0;
    for (int &i = cur[x]; ~i; i = nxt[i]) {
      edge &e = edges[i];
      if (d[e.to] == d[x] + 1 && (f = dfs(e.to, min(a, e.cap - e.flow))) > 0) {
        e.flow += f;
        edges[i ^ 1].flow -= f;
        a -= f;
        flow += f;
        if (!a)
          break;
      }
    }

    return flow;
  }

  inline int maxflow(int s, int t) {
    this->s = s;
    this->t = t;
    int flow = 0;
    while (bfs())
      flow += dfs(s, INF);
    return flow;
  }
} dinic;

int n, m;

int a[110][110], b[110][110], c[110][110];
int val[110][110];

vector<int> vec[110][110];

inline int get(int x) { return (x - 1) / m + 1; }

int main() {
  cin >> n >> m;

  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++)
      scanf("%d", &a[i][j]);

  for (int i = 1; i <= n; i++)
    for (int j = 1; j <= m; j++)
      vec[i][get(a[i][j])].push_back(a[i][j]);

  for (int i = 1; i <= m; i++) {
    dinic.init();

    dinic.L = 0, dinic.R = 2 * n + 2;
    int S = 2 * n + 1, T = 2 * n + 2;

    for (int j = 1; j <= n; j++)
      dinic.add_edge(S, j, 1);
    for (int j = 1; j <= n; j++)
      dinic.add_edge(j + n, T, 1);
    for (int j = 1; j <= n; j++)
      for (int k = 1; k <= n; k++)
        if (!vec[j][k].empty())
          dinic.add_edge(j, k + n, 1);
    dinic.maxflow(S, T);
    for (int j = 1; j <= n; j++)
      for (int k = dinic.head[j]; ~k; k = dinic.nxt[k]) {
        edge &e = dinic.edges[k];
        if (e.to != S && e.to != T && e.to > n && e.cap == e.flow) {
          b[j][i] = vec[j][e.to - n].back();
          vec[j][e.to - n].pop_back();
        }
      }
  }

  for (int i = 1; i <= m; i++) {
    static int tmp[110];
    for (int j = 1; j <= n; j++)
      tmp[j] = b[j][i];
    sort(tmp + 1, tmp + 1 + n, [](int a, int b) { return get(a) < get(b); });
    for (int j = 1; j <= n; j++)
      c[j][i] = tmp[j];
  }

  for (int i = 1; i <= n; i++, puts(""))
    for (int j = 1; j <= m; j++)
      printf("%d ", b[i][j]);
  for (int i = 1; i <= n; i++, puts(""))
    for (int j = 1; j <= m; j++)
      printf("%d ", c[i][j]);

  return 0;
}