Problem p03770 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <cmath>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <stack>
#include <vector>
using namespace std;
typedef long long lli;
typedef vector<lli> vll;
typedef vector<bool> vbl;
typedef vector<vector<lli>> mat;
typedef vector<vector<bool>> matb;
typedef vector<string> vst;
typedef pair<lli, lli> pll;
typedef pair<double, double> pdd;

const lli MOD = 1000000007;

lli n, x, y;

vll c, w;
vll min_c;
vll min_w;
mat ans;
//-------------------------------------
vll par;
vll rnk;
void init(lli n) {
  par = vll(n);
  rnk = vll(n);
  for (lli i = 0; i < n; i++)
    par[i] = i;
}
lli find(lli x) {
  if (par[x] == x)
    return x;
  else
    return par[x] = find(par[x]);
}
void unite(lli x, lli y) {
  x = find(x);
  y = find(y);
  if (x == y)
    return;
  if (rnk[x] < rnk[y])
    par[x] = y;
  else {
    par[y] = x;
    if (rnk[x] == rnk[y])
      rnk[x]++;
  }
}
bool same(lli x, lli y) { return find(x) == find(y); }
lli factrial(lli x) {
  static lli dp[100001];
  if (dp[x])
    return dp[x];
  if (x == 0)
    return dp[x] = 1;
  return dp[x] = (factrial(x - 1) * x) % MOD;
}
lli pow(lli a, lli n, lli mod = 1000000007) {
  lli ret = 1;
  for (; n != 0; n = n >> 1) {
    if (n & 1)
      ret = (ret * a) % mod;
    a = (a * a) % mod;
  }
  return ret;
}
//-------------------------------------
void solve() {
  min_c = vll(n, 1ll << 62);
  min_w = vll(n, 1ll << 62);
  for (lli i = 0; i < n; i++) {
    if (min_w[c[i]] > w[i]) {
      min_c[c[i]] = i;
      min_w[c[i]] = w[i];
    }
  }
  init(n);
  for (lli i = 0; i < n; i++) {
    if (min_w[c[i]] + w[i] <= x)
      unite(i, min_c[c[i]]);
  }
  lli all_min_elem = min_element(min_w.begin(), min_w.end()) - min_w.begin();
  lli all_min_elem_l =
      min_element(min_w.begin(), min_w.begin() + all_min_elem) - min_w.begin();
  lli all_min_elem_r =
      min_element(min_w.begin() + all_min_elem + 1, min_w.end()) -
      min_w.begin();
  lli all_min_elem_ =
      (min_w[all_min_elem_l] > min_w[all_min_elem_r] ? all_min_elem_r
                                                     : all_min_elem_l);
  for (lli i = 0; i < n; i++) {
    if (c[i] == all_min_elem) {
      if (min_w[all_min_elem_] + w[i] <= y)
        unite(i, min_c[all_min_elem_]);
    } else {
      if (min_w[all_min_elem] + w[i] <= y)
        unite(i, min_c[all_min_elem]);
    }
  }
  ans = mat(n);
  for (lli i = 0; i < n; i++) {
    ans[find(i)].push_back(i);
  }
  lli out = 1;
  for (lli i = 0; i < n; i++) {
    out *= factrial(ans[i].size());
    out %= MOD;
    map<lli, lli> col;
    for (lli j = 0; j < ans[i].size(); j++) {
      col[c[ans[i][j]]]++;
    }
    lli di = 1;
    for (auto itr = col.begin(); itr != col.end(); itr++) {
      di *= factrial(itr->second);
      di %= MOD;
    }
    out *= pow(di, MOD - 2);
    out %= MOD;
  }
  cout << out << endl;
}
void input() {
  cin >> n >> x >> y;
  c = vll(n);
  w = vll(n);
  for (lli i = 0; i < n; i++)
    cin >> c[i] >> w[i];
  for (lli i = 0; i < n; i++)
    c[i]--;
}
int main() {
  input();
  solve();
  return 0;
}

Fixed submission:
#include <algorithm>
#include <cmath>
#include <iostream>
#include <list>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <stack>
#include <vector>
using namespace std;
typedef long long lli;
typedef vector<lli> vll;
typedef vector<bool> vbl;
typedef vector<vector<lli>> mat;
typedef vector<vector<bool>> matb;
typedef vector<string> vst;
typedef pair<lli, lli> pll;
typedef pair<double, double> pdd;

const lli MOD = 1000000007;

lli n, x, y;

vll c, w;
vll min_c;
vll min_w;
mat ans;
//-------------------------------------
vll par;
vll rnk;
void init(lli n) {
  par = vll(n);
  rnk = vll(n);
  for (lli i = 0; i < n; i++)
    par[i] = i;
}
lli find(lli x) {
  if (par[x] == x)
    return x;
  else
    return par[x] = find(par[x]);
}
void unite(lli x, lli y) {
  x = find(x);
  y = find(y);
  if (x == y)
    return;
  if (rnk[x] < rnk[y])
    par[x] = y;
  else {
    par[y] = x;
    if (rnk[x] == rnk[y])
      rnk[x]++;
  }
}
bool same(lli x, lli y) { return find(x) == find(y); }
lli factrial(lli x) {
  static lli dp[200001];
  if (dp[x])
    return dp[x];
  if (x == 0)
    return dp[x] = 1;
  return dp[x] = (factrial(x - 1) * x) % MOD;
}
lli pow(lli a, lli n, lli mod = 1000000007) {
  lli ret = 1;
  for (; n != 0; n = n >> 1) {
    if (n & 1)
      ret = (ret * a) % mod;
    a = (a * a) % mod;
  }
  return ret;
}
//-------------------------------------
void solve() {
  min_c = vll(n, 1ll << 62);
  min_w = vll(n, 1ll << 62);
  for (lli i = 0; i < n; i++) {
    if (min_w[c[i]] > w[i]) {
      min_c[c[i]] = i;
      min_w[c[i]] = w[i];
    }
  }
  init(n);
  for (lli i = 0; i < n; i++) {
    if (min_w[c[i]] + w[i] <= x)
      unite(i, min_c[c[i]]);
  }
  lli all_min_elem = min_element(min_w.begin(), min_w.end()) - min_w.begin();
  lli all_min_elem_l =
      min_element(min_w.begin(), min_w.begin() + all_min_elem) - min_w.begin();
  lli all_min_elem_r =
      min_element(min_w.begin() + all_min_elem + 1, min_w.end()) -
      min_w.begin();
  lli all_min_elem_ =
      (min_w[all_min_elem_l] > min_w[all_min_elem_r] ? all_min_elem_r
                                                     : all_min_elem_l);
  for (lli i = 0; i < n; i++) {
    if (c[i] == all_min_elem) {
      if (min_w[all_min_elem_] + w[i] <= y)
        unite(i, min_c[all_min_elem_]);
    } else {
      if (min_w[all_min_elem] + w[i] <= y)
        unite(i, min_c[all_min_elem]);
    }
  }
  ans = mat(n);
  for (lli i = 0; i < n; i++) {
    ans[find(i)].push_back(i);
  }
  lli out = 1;
  for (lli i = 0; i < n; i++) {
    out *= factrial(ans[i].size());
    out %= MOD;
    map<lli, lli> col;
    for (lli j = 0; j < ans[i].size(); j++) {
      col[c[ans[i][j]]]++;
    }
    lli di = 1;
    for (auto itr = col.begin(); itr != col.end(); itr++) {
      di *= factrial(itr->second);
      di %= MOD;
    }
    out *= pow(di, MOD - 2);
    out %= MOD;
  }
  cout << out << endl;
}
void input() {
  cin >> n >> x >> y;
  c = vll(n);
  w = vll(n);
  for (lli i = 0; i < n; i++)
    cin >> c[i] >> w[i];
  for (lli i = 0; i < n; i++)
    c[i]--;
}
int main() {
  input();
  solve();
  return 0;
}