Problem p02782 (C++)

Buggy submission (status: Runtime Error):
#include <algorithm>
#include <cassert>
#include <cmath>
#include <deque>
#include <functional>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <string>
#include <vector>
#define Inf 1000000000
#define nmax_def 110000
#define mod 1000000007
#define rep(i, n) for (int(i) = 0; (i) < (n); (i)++)
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef vector<int> vi;
typedef vector<ll> vl;
typedef vector<bool> vb;

vl pow_;
void pow_ini(ll n) {
  pow_.push_back(n);
  rep(j, 62) {
    ll nxt = pow_[j] * pow_[j];
    nxt %= mod;
    pow_.push_back(nxt);
  }
  return;
}

ll pow1(ll k) {
  ll ans = 1;
  rep(ntmp, 62) {
    if ((k >> ntmp) % 2 == 1) {
      ans *= pow_[ntmp];
      ans %= mod;
    }
  }
  return ans;
}

vl fact;
vl fact_inv;

void fact_ini(ll n) {
  fact.push_back(1);
  fact.push_back(1);
  for (ll i = 2; i <= n; i++) {
    ll fact_tmp = fact[i - 1] * i;
    fact_tmp %= mod;
    fact.push_back(fact_tmp);
  }
  fact_inv.resize(n + 1);
  pow_ini(fact[n]);
  fact_inv[n] = pow1(mod - 2);
  for (ll i = n - 1; i >= 0; i--) {
    fact_inv[i] = fact_inv[i + 1] * (i + 1);
    fact_inv[i] %= mod;
  }
}

ll nCm(ll n, ll m) {
  if (fact.size() <= n)
    assert(false);
  if (fact.size() <= m)
    assert(false);
  ll ans = fact[n] * fact_inv[m];
  ans %= mod;
  ans *= fact_inv[n - m];
  ans %= mod;
  return ans;
}

int main() {
  fact_ini(1100000);
  ll r1, c1, r2, c2;
  cin >> r1 >> c1 >> r2 >> c2;
  if (r2 - r1 < c2 - c1) {
    swap(r1, c1);
    swap(r2, c2);
  }
  ll anstmp = nCm(r1 + c1, r1);
  ll ans = anstmp;
  rep(i, r2 + c2 - r1 - c1) {
    anstmp = anstmp * 2;
    anstmp %= mod;
    if (i < c2 - c1) {
      anstmp += nCm(r1 + c1 + i, c1 + i + 1);
      anstmp += nCm(r1 + c1 + i, c1 - 1);
    } else if (i < r2 - r1) {
      anstmp -= nCm(r1 + c1 + i, c2);
      anstmp += nCm(r1 + c1 + i, c1 - 1);
      anstmp += mod;
    } else {
      anstmp -= nCm(r1 + c1 + i, c2);
      anstmp -= nCm(r1 + c1 + i, r2);
      anstmp += mod;
      anstmp += mod;
    }
    anstmp %= mod;
    ans += anstmp;
    ans %= mod;
  }
  cout << ans << endl;

  return 0;
}


Fixed submission:
#include <algorithm>
#include <cassert>
#include <cmath>
#include <deque>
#include <functional>
#include <iostream>
#include <map>
#include <queue>
#include <set>
#include <string>
#include <vector>
#define Inf 1000000000
#define nmax_def 110000
#define mod 1000000007
#define rep(i, n) for (int(i) = 0; (i) < (n); (i)++)
using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef vector<int> vi;
typedef vector<ll> vl;
typedef vector<bool> vb;

vl pow_;
void pow_ini(ll n) {
  pow_.push_back(n);
  rep(j, 62) {
    ll nxt = pow_[j] * pow_[j];
    nxt %= mod;
    pow_.push_back(nxt);
  }
  return;
}

ll pow1(ll k) {
  ll ans = 1;
  rep(ntmp, 62) {
    if ((k >> ntmp) % 2 == 1) {
      ans *= pow_[ntmp];
      ans %= mod;
    }
  }
  return ans;
}

vl fact;
vl fact_inv;

void fact_ini(ll n) {
  fact.push_back(1);
  fact.push_back(1);
  for (ll i = 2; i <= n; i++) {
    ll fact_tmp = fact[i - 1] * i;
    fact_tmp %= mod;
    fact.push_back(fact_tmp);
  }
  fact_inv.resize(n + 1);
  pow_ini(fact[n]);
  fact_inv[n] = pow1(mod - 2);
  for (ll i = n - 1; i >= 0; i--) {
    fact_inv[i] = fact_inv[i + 1] * (i + 1);
    fact_inv[i] %= mod;
  }
}

ll nCm(ll n, ll m) {
  if (fact.size() <= n)
    assert(false);
  if (fact.size() <= m)
    assert(false);
  ll ans = fact[n] * fact_inv[m];
  ans %= mod;
  ans *= fact_inv[n - m];
  ans %= mod;
  return ans;
}

int main() {
  fact_ini(11000000);
  ll r1, c1, r2, c2;
  cin >> r1 >> c1 >> r2 >> c2;
  if (r2 - r1 < c2 - c1) {
    swap(r1, c1);
    swap(r2, c2);
  }
  ll anstmp = nCm(r1 + c1, r1);
  ll ans = anstmp;
  rep(i, r2 + c2 - r1 - c1) {
    anstmp = anstmp * 2;
    anstmp %= mod;
    if (i < c2 - c1) {
      anstmp += nCm(r1 + c1 + i, c1 + i + 1);
      anstmp += nCm(r1 + c1 + i, c1 - 1);
    } else if (i < r2 - r1) {
      anstmp -= nCm(r1 + c1 + i, c2);
      anstmp += nCm(r1 + c1 + i, c1 - 1);
      anstmp += mod;
    } else {
      anstmp -= nCm(r1 + c1 + i, c2);
      anstmp -= nCm(r1 + c1 + i, r2);
      anstmp += mod;
      anstmp += mod;
    }
    anstmp %= mod;
    ans += anstmp;
    ans %= mod;
  }
  cout << ans << endl;

  return 0;
}