Problem p03184 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
using namespace std;
#define what_is(x) cerr << #x << " is " << x << endl;
#define IOS                                                                    \
  ios::sync_with_stdio(false);                                                 \
  cin.tie(0);
typedef long long ll;
const int N = 3e3 + 5;
const int INF = 1e9;
const int MOD = 1e9 + 7;

int main() {
  IOS freopen("input.txt", "r", stdin);
  int h, w, n;
  cin >> h >> w >> n;
  vector<pair<int, int>> bl(n); // block
  for (int i = 0; i < n; i++) {
    cin >> bl[i].first >> bl[i].second;
    bl[i].first--; // size ak
    bl[i].second--;
  }
  bl.emplace_back(h - 1, w - 1);
  n++;
  sort(bl.begin(), bl.end());
  vector<ll> inv(h + w + 1); // inverse: phan so
  vector<ll> fact(h + w + 1);
  vector<ll> fact_inv(h + w + 1);
  inv[1] = 1;
  for (int i = 2; i < h + w + 1; i++) {
    inv[i] = MOD - (MOD / i) * inv[MOD % i] % MOD; // 1/n
  }
  fact[0] = 1;     // n!
  fact_inv[0] = 1; // 1/n!
  for (int i = 1; i < h + w + 1; i++) {
    fact[i] = fact[i - 1] * i % MOD;
    fact_inv[i] = fact_inv[i - 1] * inv[i] % MOD;
  }
  auto comb = [&](int n, int k) {
    if (n < 0 || k < 0)
      return 0LL;
    if (n < k)
      return 0LL;
    return fact[n] * fact_inv[n - k] % MOD * fact_inv[k] % MOD;
  };
  auto f = [&](int x, int y) { return comb(x + y, y); };
  vector<ll> dp(n);
  for (int i = 0; i < n; i++) {
    dp[i] = f(bl[i].first, bl[i].second);
    for (int j = 0; j < i; j++) {
      if (bl[i].second >= bl[j].second) {
        dp[i] =
            (dp[i] -
             dp[j] * f(bl[i].first - bl[j].first, bl[i].second - bl[j].second) %
                 MOD +
             MOD) %
            MOD;
      }
    }
  }
  cout << dp[n - 1] << endl;

  return 0;
}


Fixed submission:
#include <bits/stdc++.h>
using namespace std;
#define what_is(x) cerr << #x << " is " << x << endl;
#define IOS                                                                    \
  ios::sync_with_stdio(false);                                                 \
  cin.tie(0);
typedef long long ll;
const int N = 3e3 + 5;
const int INF = 1e9;
const int MOD = 1e9 + 7;

int main() {
  IOS
      // freopen("input.txt", "r", stdin);
      int h,
      w, n;
  cin >> h >> w >> n;
  vector<pair<int, int>> bl(n); // block
  for (int i = 0; i < n; i++) {
    cin >> bl[i].first >> bl[i].second;
    bl[i].first--; // size ak
    bl[i].second--;
  }
  bl.emplace_back(h - 1, w - 1);
  n++;
  sort(bl.begin(), bl.end());
  vector<ll> inv(h + w + 1); // inverse: phan so
  vector<ll> fact(h + w + 1);
  vector<ll> fact_inv(h + w + 1);
  inv[1] = 1;
  for (int i = 2; i < h + w + 1; i++) {
    inv[i] = MOD - (MOD / i) * inv[MOD % i] % MOD; // 1/n
  }
  fact[0] = 1;     // n!
  fact_inv[0] = 1; // 1/n!
  for (int i = 1; i < h + w + 1; i++) {
    fact[i] = fact[i - 1] * i % MOD;
    fact_inv[i] = fact_inv[i - 1] * inv[i] % MOD;
  }
  auto comb = [&](int n, int k) {
    if (n < 0 || k < 0)
      return 0LL;
    if (n < k)
      return 0LL;
    return fact[n] * fact_inv[n - k] % MOD * fact_inv[k] % MOD;
  };
  auto f = [&](int x, int y) { return comb(x + y, y); };
  vector<ll> dp(n);
  for (int i = 0; i < n; i++) {
    dp[i] = f(bl[i].first, bl[i].second);
    for (int j = 0; j < i; j++) {
      if (bl[i].second >= bl[j].second) {
        dp[i] =
            (dp[i] -
             dp[j] * f(bl[i].first - bl[j].first, bl[i].second - bl[j].second) %
                 MOD +
             MOD) %
            MOD;
      }
    }
  }
  cout << dp[n - 1] << endl;

  return 0;
}