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

#include <algorithm>
#include <deque>
#include <iostream>
#include <numeric>
#include <queue>
#include <tuple>
#include <vector>
using namespace std;

struct GeneralMatching {
  int N;
  int cur;
  vector<int> t, p, used, base, match;
  queue<int> que;
  vector<vector<int>> G;

  GeneralMatching(int n)
      : N(n), cur(0), t(n), p(n), used(n), base(n), match(n), G(n) {}

  void addEdge(int v, int u) {
    G[v].push_back(u);
    G[u].push_back(v);
  }

  int get(int v) { return base[v] == v ? v : base[v] = get(base[v]); }

  int getLCA(int v, int u) {
    v = get(v);
    u = get(u);
    cur++;
    while (true) {
      if (v != -1) {
        if (used[v] == cur)
          return v;
        used[v] = cur;
        v = match[v] == -1 ? -1 : get(p[match[v]]);
      }
      swap(v, u);
    }
  }

  void blossom(int v, int u, int b) {
    while (get(v) != b) {
      p[v] = u;
      u = match[v];
      if (t[u] == 1) {
        t[u] = 0;
        que.push(u);
      }
      base[v] = b;
      base[u] = b;
      v = p[u];
    }
  }

  void augment(int u, int v) {
    while (u != -1) {
      int nu = match[p[u]];
      match[u] = p[u];
      match[p[u]] = u;
      u = nu;
    }
  }

  bool bfs(int s) {
    fill(p.begin(), p.end(), -1);
    fill(t.begin(), t.end(), -1);
    iota(base.begin(), base.end(), 0);
    t[s] = 0;
    que = queue<int>();
    que.push(s);
    while (que.size()) {
      int v = que.front();
      que.pop();
      for (auto u : G[v]) {
        if (t[u] == -1) {
          t[u] = 1;
          p[u] = v;
          if (match[u] == -1) {
            augment(u, v);
            return true;
          }
          int w = match[u];
          t[w] = 0;
          que.push(w);
        } else if (t[u] == 0 && get(v) != get(u)) {
          int b = getLCA(v, u);
          blossom(v, u, b);
          blossom(u, v, b);
        }
      }
    }
    return false;
  }
  int solve() {
    fill(match.begin(), match.end(), -1);
    int res = 0;
    for (int i = 0; i < N; i++) {
      if (match[i] == -1 && bfs(i))
        res++;
    }
    return res;
  }
};

int main() {
  int X, Y, E;
  cin >> X >> Y >> E;

  GeneralMatching gm(X + Y);
  for (int i = 0; i < E; i++) {
    int x, y;
    cin >> x >> y;
    y += X;
    gm.addEdge(x, y);
  }

  cout << gm.solve() << endl;
  return 0;
}


Error: TLE

Fixed submission:

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

#define int long long

typedef pair<int, int> pint;
typedef vector<int> vint;
typedef vector<pint> vpint;
#define pb push_back
#define mp make_pair
#define fi first
#define se second
#define all(v) (v).begin(), (v).end()
#define rep(i, n) for (int i = 0; i < (n); i++)
#define reps(i, f, n) for (int i = (f); i < (n); i++)
#define each(it, v)                                                            \\
  for (__typeof((v).begin()) it = (v).begin(); it != (v).end(); it++)
template <class T, class U> void chmin(T &t, U f) {
  if (t > f)
    t = f;
}
template <class T, class U> void chmax(T &t, U f) {
  if (t < f)
    t = f;
}

using Num = double;
using Vec = vector<Num>;
using Mat = vector<Vec>;
const Num Inf = numeric_limits<Num>::infinity();
const Num NoSolution = numeric_limits<Num>::quiet_NaN();
Num EPS = 1e-10;
/*
min c*x
s.t. A*x<=b
     x>=0
*/

Num simplex(const Mat &A, const Vec &b, const Vec &c) {
  const int m = A.size(), n = A[0].size();

  Mat D(m + 1, Vec(n + m + 1));
  Vec id(m + n);
  for (int i = 0; i < m; i++) {
    for (int j = 0; j < n; j++)
      D[i][j] = A[i][j];
    D[i][n + i] = 1;
    D[i][n + m] = -b[i];
  }
  for (int i = 0; i < n; i++)
    D[m][i] = c[i];

  for (int i = 0; i < m; i++)
    id[i] = n + i;
  for (int i = 0; i < n; i++)
    id[m + i] = i;

  while (true) {
    int r = n;
    for (int i = n - 1; i >= 0; i--)
      if (D[m][id[m + i]] < -EPS)
        r = i;
    if (r == n)
      return D[m][n + m];
    int s = m;
    for (int i = 0; i < m; i++)
      if (D[i][id[m + r]] > EPS) {
        if (s == m ||
            -D[s][n + m] / D[s][id[m + r]] > -D[i][n + m] / D[i][id[m + r]])
          s = i;
      }
    if (s == m)
      return Inf; // NoBound
    Num k = D[s][id[m + r]];
    for (int i = 0; i <= n + m; i++)
      D[s][i] /= k;
    for (int i = 0; i <= m; i++) {
      if (i == s)
        continue;
      k = D[i][id[m + r]];
      for (int j = 0; j <= n + m; j++)
        D[i][j] -= k * D[s][j];
    }
    swap(id[s], id[m + r]);
  }
}

int X, Y, E;

int x[111][11111], y[111][11111];

signed main() {
  cin >> X >> Y >> E;
  rep(i, E) {
    int a, b;
    cin >> a >> b;
    x[a][i] = 1;
    y[b][i] = 1;
  }

  Mat A;
  Vec b, c(E);
  rep(i, E) c[i] = -1;
  for (int i = 0; i < X; i++) {
    Vec v(E);
    rep(j, E) v[j] = x[i][j];
    A.pb(v);
    b.pb(1);
  }
  for (int i = 0; i < Y; i++) {
    Vec v(E);
    rep(j, E) v[j] = y[i][j];
    A.pb(v);
    b.pb(1);
  }
  /*
  rep(i,E){
      Vec v(E);v[i]=1;
      A.pb(v);b.pb(1);
  }*/

  Num t = -simplex(A, b, c);
  int s = round(t);
  if (abs(t - s) > 0.01)
    assert(0);
  cout << s << endl;
  return 0;
}