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

#include <algorithm>
#include <cstdio>

#define rep(i, n) for (int i = 0; i < (n); i++)

using namespace std;

const int INF = 1 << 29;

const int V_MAX = 202;
const int E_MAX = 2 * 100 + 100 * 100;

template <class T> struct graph {
  int n, m, head[V_MAX], next[2 * E_MAX], to[2 * E_MAX];
  T capa[2 * E_MAX], flow[2 * E_MAX];

  void init(int N) {
    n = N;
    m = 0;
    rep(u, n) head[u] = -1;
  }

  void add_directed_edge(int u, int v, T ca) {
    next[m] = head[u];
    head[u] = m;
    to[m] = v;
    capa[m] = ca;
    flow[m] = 0;
    m++;
    next[m] = head[v];
    head[v] = m;
    to[m] = u;
    capa[m] = 0;
    flow[m] = 0;
    m++;
  }

  void add_undirected_edge(int u, int v, T ca) {
    next[m] = head[u];
    head[u] = m;
    to[m] = v;
    capa[m] = ca;
    flow[m] = 0;
    m++;
    next[m] = head[v];
    head[v] = m;
    to[m] = u;
    capa[m] = ca;
    flow[m] = 0;
    m++;
  }
};

int layer[V_MAX], now[V_MAX];

template <class T> bool make_layer(const graph<T> &G, int s, int t) {
  int n = G.n;
  rep(u, n) layer[u] = (u == s ? 0 : -1);

  int head = 0, tail = 0;
  static int Q[V_MAX];
  Q[tail++] = s;
  while (head < tail && layer[t] == -1) {
    int u = Q[head++];

    for (int e = G.head[u]; e != -1; e = G.next[e]) {
      int v = G.to[e];
      T capa = G.capa[e], flow = G.flow[e];

      if (capa - flow > 0 && layer[v] == -1) {
        layer[v] = layer[u] + 1;
        Q[tail++] = v;
      }
    }
  }

  return layer[t] != -1;
}

template <class T> T augment(graph<T> &G, int u, int t, T water) {
  if (u == t)
    return water;

  for (int &e = now[u]; e != -1; e = G.next[e]) {
    int v = G.to[e];
    T capa = G.capa[e], flow = G.flow[e];

    if (capa - flow > 0 && layer[v] > layer[u]) {
      T w = augment(G, v, t, min(water, capa - flow));
      if (w > 0) {
        G.flow[e] += w;
        G.flow[e ^ 1] -= w;
        return w;
      }
    }
  }
  return 0;
}

template <class T> T Dinic(graph<T> &G, int s, int t) {
  int n = G.n;
  T ans = 0;
  while (make_layer(G, s, t)) {
    rep(u, n) now[u] = G.head[u];
    for (T water = 1; water > 0; ans += water)
      water = augment(G, s, t, INF);
  }
  return ans;
}

int main() {
  for (int n, m, L; ~scanf("%d%d%d", &n, &m, &L);) {
    static int d[100][100];
    rep(u, n) rep(v, n) d[u][v] = (u == v ? 0 : INF);
    rep(i, m) {
      int u, v, cost;
      scanf("%d%d%d", &u, &v, &cost);
      u--;
      v--;
      d[u][v] = d[v][u] = cost;
    }

    int ini[100], cap[100];
    rep(u, n) scanf("%d", ini + u);
    rep(u, n) scanf("%d", cap + u);

    rep(k, n) rep(i, n) rep(j, n) d[i][j] = min(d[i][j], d[i][k] + d[k][j]);

    int s = 2 * n, t = 2 * n + 1;
    static graph<int> G;
    G.init(2 * n + 2);
    rep(u, n) {
      G.add_directed_edge(s, 2 * u, ini[u]);
      G.add_directed_edge(2 * u + 1, t, cap[u]);
      rep(v, n) if (d[u][v] < L) G.add_directed_edge(2 * u, 2 * v + 1, INF);
    }
    printf("%d\\n", Dinic(G, s, t));
  }

  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <cstdio>

#define rep(i, n) for (int i = 0; i < (n); i++)

using namespace std;

const int INF = 1 << 29;

const int V_MAX = 100;
const int E_MAX = 10000;

template <class T> struct graph {
  int n, m, head[V_MAX], next[2 * E_MAX], to[2 * E_MAX];
  T capa[2 * E_MAX], flow[2 * E_MAX];

  void init(int N) {
    n = N;
    m = 0;
    rep(u, n) head[u] = -1;
  }

  void add_directed_edge(int u, int v, T ca) {
    next[m] = head[u];
    head[u] = m;
    to[m] = v;
    capa[m] = ca;
    flow[m] = 0;
    m++;
    next[m] = head[v];
    head[v] = m;
    to[m] = u;
    capa[m] = 0;
    flow[m] = 0;
    m++;
  }

  void add_undirected_edge(int u, int v, T ca) {
    next[m] = head[u];
    head[u] = m;
    to[m] = v;
    capa[m] = ca;
    flow[m] = 0;
    m++;
    next[m] = head[v];
    head[v] = m;
    to[m] = u;
    capa[m] = ca;
    flow[m] = 0;
    m++;
  }
};

int layer[V_MAX], now[V_MAX];

template <class T> bool make_layer(const graph<T> &G, int s, int t) {
  int n = G.n;
  rep(u, n) layer[u] = (u == s ? 0 : -1);

  int head = 0, tail = 0;
  static int Q[V_MAX];
  Q[tail++] = s;
  while (head < tail && layer[t] == -1) {
    int u = Q[head++];

    for (int e = G.head[u]; e != -1; e = G.next[e]) {
      int v = G.to[e];
      T capa = G.capa[e], flow = G.flow[e];

      if (capa - flow > 0 && layer[v] == -1) {
        layer[v] = layer[u] + 1;
        Q[tail++] = v;
      }
    }
  }

  return layer[t] != -1;
}

template <class T> T augment(graph<T> &G, int u, int t, T water) {
  if (u == t)
    return water;

  for (int &e = now[u]; e != -1; e = G.next[e]) {
    int v = G.to[e];
    T capa = G.capa[e], flow = G.flow[e];

    if (capa - flow > 0 && layer[v] > layer[u]) {
      T w = augment(G, v, t, min(water, capa - flow));
      if (w > 0) {
        G.flow[e] += w;
        G.flow[e ^ 1] -= w;
        return w;
      }
    }
  }
  return 0;
}

template <class T> T Dinic(graph<T> &G, int s, int t) {
  int n = G.n;
  T ans = 0;
  while (make_layer(G, s, t)) {
    rep(u, n) now[u] = G.head[u];
    for (T water = 1; water > 0; ans += water)
      water = augment(G, s, t, INF);
  }
  return ans;
}

int main() {
  for (int n, m, L; ~scanf("%d%d%d", &n, &m, &L);) {
    static int d[100][100];
    rep(u, n) rep(v, n) d[u][v] = (u == v ? 0 : INF);
    rep(i, m) {
      int u, v, cost;
      scanf("%d%d%d", &u, &v, &cost);
      u--;
      v--;
      d[u][v] = d[v][u] = min(d[u][v], cost);
    }

    int ini[100], cap[100];
    rep(u, n) scanf("%d", ini + u);
    rep(u, n) scanf("%d", cap + u);

    rep(k, n) rep(i, n) rep(j, n) d[i][j] = min(d[i][j], d[i][k] + d[k][j]);

    int s = n, t = n + 1;
    static graph<int> G;
    G.init(n + 2);
    rep(u, n) {
      G.add_directed_edge(s, u, ini[u]);
      G.add_directed_edge(u, t, cap[u]);
      rep(v, u) if (d[u][v] < L) G.add_undirected_edge(u, v, INF);
    }
    printf("%d\\n", Dinic(G, s, t));
  }

  return 0;
}