Problem p03770 (C++)

Buggy submission (status: Time Limit Exceeded):
#include <bits/stdc++.h>

// #define int long long
#define ll long long
#define F first
#define S second
#define pb push_back
#define ld long double

using namespace std;

const int MAXN = 201 * 1001, MOD = 1e9 + 7, L = 18;

int n, x, y;

int fact[MAXN], inv[MAXN];

int tv(int x, int y) {
  if (!y)
    return 1;
  ll ans = tv(x, y / 2);
  ans *= ans, ans %= MOD;
  if (y & 1)
    ans *= x;
  return ans % MOD;
}

int c[MAXN], w[MAXN];

priority_queue<pair<int, int>> s[40];

unordered_map<int, int> cnt[MAXN];

set<int> S[MAXN];
/*
inline void erase(int c , int w )
{
        S[c].erase(w) ;
        for(int i = 0 ; i < L ; i ++ ) {
                if(c&(1<<i))
                        s[i].erase({w,c}) ;
                else
                        s[i+L].erase({w,c});
        }

}
*/
vector<pair<int, int>> v;

void dfs(int C, int W) {
  //	cout << '*' << C << ' ' << W << endl ;
  v.pb({C, cnt[C][W]});
  S[C].erase(W);
  //	erase(C,W) ;

  if (!cnt[C][W])
    return;

  cnt[C][W] = 0;

  //	v.pb({C,W}) ;
  int w = y - W;
  // cout << w << endl ;
  for (int i = 0; i < 2 * L; i += rand() & 1) {
    if (C & (1 << i) && i < L)
      continue;
    if (!(C & (1 << (i - L))) && i >= L)
      continue;
    //	if(C==3&&W==2)cout << i << endl ;
    //	if(i==20) cout << ' ' << s[i].size() << (s[i].begin()->F) << endl ;
    while (s[i].size()) {
      pair<int, int> p = s[i].top();
      p.F *= -1;
      if (p.F > w)
        break;
      s[i].pop();
      dfs(p.S, p.F);
    }
  }

  w = x - W;
  while (S[C].size() && *S[C].begin() <= w) {
    dfs(C, *S[C].begin());
  }
}

int32_t main() {
  //	ios::sync_with_stdio(0) ;
  fact[0] = inv[0] = 1;
  for (int i = 1; i < MAXN; i++)
    fact[i] = 1LL * i * fact[i - 1] % MOD, inv[i] = tv(fact[i], MOD - 2);
  //	s[0].push({1,2}) ;
  //	s[0].push({2,3}) ;
  //	cout << s[0].top().F << endl ;
  //	cin >> n >> x >> y ;
  scanf("%d%d%d", &n, &x, &y);
  for (int i = 0; i < n; i++) {
    // cin >> c[i] >> w[i] ;
    scanf("%d%d", &c[i], &w[i]);
    cnt[c[i]][w[i]]++;
    for (int j = 0; j < L; j++) {
      if (c[i] & (1 << j))
        s[j].push({-w[i], c[i]});
      else {
        //			if(c[i]==2) cout << '&' << j << endl ;
        s[j + L].push({-w[i], c[i]});
      }
    }
    S[c[i]].insert(w[i]);
  }
  ll ans = 1;
  for (int i = 0; i < n; i++) {
    if (!cnt[c[i]][w[i]])
      continue;
    v.clear();
    dfs(c[i], w[i]);
    int C = 0;
    sort(v.begin(), v.end());
    int prv = -1, x = 0;
    for (auto u : v) {
      //		cout << u.F << ' ' << u.S << endl ;
      C += u.S;
      if (u.F == prv)
        x += u.S;
      else
        ans *= inv[x], ans %= MOD, prv = u.F, x = u.S;
    }
    //	cout << endl << endl ;
    ans *= inv[x];
    ans %= MOD;
    ans *= fact[C];
    ans %= MOD;
    //	cout << C << endl ;
  }
  cout << ans << endl;
}


Fixed submission:
#include <bits/stdc++.h>

// #define int long long
#define ll long long
#define F first
#define S second
#define pb push_back
#define ld long double

using namespace std;

const int MAXN = 201 * 1001, MOD = 1e9 + 7, L = 18;

int n, x, y;

int fact[MAXN], inv[MAXN];

int tv(int x, int y) {
  if (!y)
    return 1;
  ll ans = tv(x, y / 2);
  ans *= ans, ans %= MOD;
  if (y & 1)
    ans *= x;
  return ans % MOD;
}

int c[MAXN], w[MAXN];

priority_queue<pair<int, int>> s[40];

unordered_map<int, int> cnt[MAXN];

set<int> S[MAXN];
/*
inline void erase(int c , int w )
{
        S[c].erase(w) ;
        for(int i = 0 ; i < L ; i ++ ) {
                if(c&(1<<i))
                        s[i].erase({w,c}) ;
                else
                        s[i+L].erase({w,c});
        }

}
*/
vector<pair<int, int>> v;

void dfs(int C, int W) {
  //	cout << '*' << C << ' ' << W << endl ;
  v.pb({C, cnt[C][W]});
  S[C].erase(W);
  //	erase(C,W) ;

  if (!cnt[C][W])
    return;

  cnt[C][W] = 0;

  //	v.pb({C,W}) ;
  int w = y - W;
  // cout << w << endl ;
  for (int i = 0; i < 2 * L; i += rand() % 3) {
    if (C & (1 << i) && i < L)
      continue;
    if (!(C & (1 << (i - L))) && i >= L)
      continue;
    //	if(C==3&&W==2)cout << i << endl ;
    //	if(i==20) cout << ' ' << s[i].size() << (s[i].begin()->F) << endl ;
    while (s[i].size()) {
      pair<int, int> p = s[i].top();
      p.F *= -1;
      if (p.F > w)
        break;
      s[i].pop();
      dfs(p.S, p.F);
    }
  }

  w = x - W;
  while (S[C].size() && *S[C].begin() <= w) {
    dfs(C, *S[C].begin());
  }
}

int32_t main() {
  //	ios::sync_with_stdio(0) ;
  fact[0] = inv[0] = 1;
  for (int i = 1; i < MAXN; i++)
    fact[i] = 1LL * i * fact[i - 1] % MOD, inv[i] = tv(fact[i], MOD - 2);
  //	s[0].push({1,2}) ;
  //	s[0].push({2,3}) ;
  //	cout << s[0].top().F << endl ;
  //	cin >> n >> x >> y ;
  scanf("%d%d%d", &n, &x, &y);
  for (int i = 0; i < n; i++) {
    // cin >> c[i] >> w[i] ;
    scanf("%d%d", &c[i], &w[i]);
    cnt[c[i]][w[i]]++;
    for (int j = 0; j < L; j++) {
      if (c[i] & (1 << j))
        s[j].push({-w[i], c[i]});
      else {
        //			if(c[i]==2) cout << '&' << j << endl ;
        s[j + L].push({-w[i], c[i]});
      }
    }
    S[c[i]].insert(w[i]);
  }
  ll ans = 1;
  for (int i = 0; i < n; i++) {
    if (!cnt[c[i]][w[i]])
      continue;
    v.clear();
    dfs(c[i], w[i]);
    int C = 0;
    sort(v.begin(), v.end());
    int prv = -1, x = 0;
    for (auto u : v) {
      //		cout << u.F << ' ' << u.S << endl ;
      C += u.S;
      if (u.F == prv)
        x += u.S;
      else
        ans *= inv[x], ans %= MOD, prv = u.F, x = u.S;
    }
    //	cout << endl << endl ;
    ans *= inv[x];
    ans %= MOD;
    ans *= fact[C];
    ans %= MOD;
    //	cout << C << endl ;
  }
  cout << ans << endl;
}