Problem p03823 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
#define rep(i, j, k) for (int i = (int)j; i <= (int)k; i++)
#define per(i, j, k) for (int i = (int)j; i >= (int)k; i--)
using namespace std;
typedef long long LL;
const int P = 1000000007;
const int N = 110000;
inline void add(int &a, int b) {
  a += b;
  if (a >= P)
    a -= P;
}
inline void dec(int &a, int b) {
  a -= b;
  if (a < 0)
    a += P;
}
int n;
LL a[N];
LL A, B;
int f[N][3];
LL mes[N << 2];
void build(int me, int l, int r) {
  if (l == r) {
    mes[me] = a[l + 1] - a[l];
    return;
  }
  int mid = (l + r) >> 1;
  build(me << 1, l, mid);
  build(me << 1 | 1, mid + 1, r);
  mes[me] = min(mes[me << 1], mes[me << 1 | 1]);
}
LL _ask(int me, int l, int r, int x, int y) {
  if (x > y)
    return max(A, B) + 10;
  if (x <= l && r <= y)
    return mes[me];
  int mid = (l + r) >> 1;
  LL ret = max(A, B) + 10;
  if (x <= mid)
    ret = min(ret, _ask(me << 1, l, mid, x, y));
  if (y > mid)
    ret = min(ret, _ask(me << 1 | 1, mid + 1, r, x, y));
  return ret;
}
LL ask(int l, int r) { return _ask(1, 1, n - 1, l, r); }
int findit(LL S) {
  int l = 1;
  int r = n;
  int ret = n + 1;
  while (l < r) {
    int mid = (l + r) >> 1;
    if (a[mid] >= S)
      ret = mid, r = mid;
    else
      l = mid + 1;
  }
  if (a[l] >= S)
    ret = l;
  return ret;
}
int main() {
  scanf("%d%lld%lld", &n, &A, &B);
  if (n == 1)
    return 2;
  rep(i, 1, n) scanf("%lld", &a[i]);
  build(1, 1, n - 1);

  f[0][2] = 1;
  rep(i, 0, n) {
    // 0 is A
    // 1 is B
    int gt = 0;
    if (f[i][0]) {
      gt = findit(a[i] + A);
      if (gt == i + 1)
        add(f[i][2], f[i][0]);
      else if (ask(i + 1, gt - 2) >= B)
        add(f[gt - 1][1], f[i][0]);
    }
    if (f[i][1]) {
      gt = findit(a[i] + B);
      if (gt == i + 1)
        add(f[i][2], f[i][1]);
      else if (ask(i + 1, gt - 2) >= A)
        add(f[gt - 1][0], f[i][1]);
    }

    add(f[i + 1][0], f[i][2]);
    add(f[i + 1][1], f[i][2]);
  }
  int ans = f[n][2];
  printf("%d\n", ans);
  return 0;
}


Fixed submission:
#include <bits/stdc++.h>
#define rep(i, j, k) for (int i = (int)j; i <= (int)k; i++)
#define per(i, j, k) for (int i = (int)j; i >= (int)k; i--)
using namespace std;
typedef long long LL;
const int P = 1000000007;
const int N = 110000;
inline void add(int &a, int b) {
  a += b;
  if (a >= P)
    a -= P;
}
inline void dec(int &a, int b) {
  a -= b;
  if (a < 0)
    a += P;
}
int n;
LL a[N];
LL A, B;
int f[N][3];
LL mes[N << 2];
void build(int me, int l, int r) {
  if (l == r) {
    mes[me] = a[l + 1] - a[l];
    return;
  }
  int mid = (l + r) >> 1;
  build(me << 1, l, mid);
  build(me << 1 | 1, mid + 1, r);
  mes[me] = min(mes[me << 1], mes[me << 1 | 1]);
}
LL _ask(int me, int l, int r, int x, int y) {
  if (x > y)
    return max(A, B) + 10;
  if (x <= l && r <= y)
    return mes[me];
  int mid = (l + r) >> 1;
  LL ret = max(A, B) + 10;
  if (x <= mid)
    ret = min(ret, _ask(me << 1, l, mid, x, y));
  if (y > mid)
    ret = min(ret, _ask(me << 1 | 1, mid + 1, r, x, y));
  return ret;
}
LL ask(int l, int r) { return _ask(1, 1, n - 1, l, r); }
int findit(LL S) {
  int l = 1;
  int r = n;
  int ret = n + 1;
  while (l < r) {
    int mid = (l + r) >> 1;
    if (a[mid] >= S)
      ret = mid, r = mid;
    else
      l = mid + 1;
  }
  if (a[l] >= S)
    ret = l;
  return ret;
}
int main() {
  scanf("%d%lld%lld", &n, &A, &B);
  if (n == 1) {
    printf("2\n");
    return 0;
  }
  rep(i, 1, n) scanf("%lld", &a[i]);
  build(1, 1, n - 1);

  f[0][2] = 1;
  rep(i, 0, n) {
    // 0 is A
    // 1 is B
    int gt = 0;
    if (f[i][0]) {
      gt = findit(a[i] + A);
      if (gt == i + 1)
        add(f[i][2], f[i][0]);
      else if (ask(i + 1, gt - 2) >= B)
        add(f[gt - 1][1], f[i][0]);
    }
    if (f[i][1]) {
      gt = findit(a[i] + B);
      if (gt == i + 1)
        add(f[i][2], f[i][1]);
      else if (ask(i + 1, gt - 2) >= A)
        add(f[gt - 1][0], f[i][1]);
    }

    add(f[i + 1][0], f[i][2]);
    add(f[i + 1][1], f[i][2]);
  }
  int ans = f[n][2];
  printf("%d\n", ans);
  return 0;
}