Problem p02824 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
#include <math.h>
#define _GLIBCXX_DEBUG
#define _LIBCPP_DEBUG 0

using namespace std;
#define ll long long
#define rep(i, n) for (int i = 0; i < n; i++)
#define rrep(i, n) for (int i = n - 1; i >= 0; i--)
#define MOD (1000000007)
#define vi vector<int>
#define vl vector<ll>
#define vb vector<bool>
#define vvi vector<vi>
#define vvl vector<vl>
#define pii pair<int, int>
#define pli pair<ll, int> a
#define pb push_back

#define mp make_pair
#define all(a) (a).begin(), (a).end()

template <class T> inline bool chmax(T &a, T b) {
  if (a < b) {
    a = b;
    return true;
  }
  return false;
}
template <class T> inline bool chmin(T &a, T b) {
  if (a > b) {
    a = b;
    return true;
  }
  return false;
}

ll gcd(ll a, ll b) {
  if (b == 0)
    return a;
  else
    return gcd(b, a % b);
}

ll keta(ll n) {
  string s = to_string(n);
  ll num = s.size();
  return num;
}

const ll INF = 1LL << 60;

const int dh[4] = {1, 0, -1, 0};
const int dw[4] = {0, 1, 0, -1};

struct Edge {
  int to;
  int weight;
  Edge(int t, int w) : to(t), weight(w) {}
};
using Graph = vector<vector<Edge>>;
using P = pair<ll, int>;

class UnionFind {
public:
  vi Parent;
  UnionFind(int n) { Parent = vi(n, -1); }

  int root(int a) {
    if (Parent[a] < 0)
      return a;
    else
      return Parent[a] = root(Parent[a]);
  }

  int size(int a) { return -Parent[root(a)]; }

  bool merge(int a, int b) {
    a = root(a);
    b = root(b);
    if (a == b)
      return false;

    if (size(a) < size(b))
      swap(a, b);
    Parent[a] += Parent[b];
    Parent[b] = a;

    return true;
  }
};

class Factrial {
public:
  vl Fac;
  Factrial(int MAX) {
    Fac = vl(MAX + 1);
    rep(i, MAX) {
      if (i == 0)
        Fac[i + 1] = 1;
      else
        Fac[i + 1] = ((i + 1) * Fac[i]) % MOD;
    }
  }
};

ll n, m, v, p;
vl a;
vl s;

bool check(int X) {
  if (X <= p - 1)
    return true;
  if (a[p - 1] - a[X] > m)
    return false;

  // 票の受け皿の数
  ll num = n * m + (X - p + 1) * a[X] - (s[X] - s[p - 1]);
  return num >= m * v;
}

int main() {
  cin >> n >> m >> v >> p;
  a.resize(n);

  rep(i, n) cin >> a[i];

  sort(all(a), greater<ll>());

  s.resize(n + 1);
  rep(i, n) s[i + 1] = s[i] + a[i];

  rrep(i, n) {
    if (check(i))
      return i + 1;
  }
}

Fixed submission:
#include <bits/stdc++.h>
#include <math.h>
#define _GLIBCXX_DEBUG
#define _LIBCPP_DEBUG 0

using namespace std;
#define ll long long
#define rep(i, n) for (int i = 0; i < n; i++)
#define rrep(i, n) for (int i = n - 1; i >= 0; i--)
#define MOD (1000000007)
#define vi vector<int>
#define vl vector<ll>
#define vb vector<bool>
#define vvi vector<vi>
#define vvl vector<vl>
#define pii pair<int, int>
#define pli pair<ll, int> a
#define pb push_back

#define mp make_pair
#define all(a) (a).begin(), (a).end()

template <class T> inline bool chmax(T &a, T b) {
  if (a < b) {
    a = b;
    return true;
  }
  return false;
}
template <class T> inline bool chmin(T &a, T b) {
  if (a > b) {
    a = b;
    return true;
  }
  return false;
}

ll gcd(ll a, ll b) {
  if (b == 0)
    return a;
  else
    return gcd(b, a % b);
}

ll keta(ll n) {
  string s = to_string(n);
  ll num = s.size();
  return num;
}

const ll INF = 1LL << 60;

const int dh[4] = {1, 0, -1, 0};
const int dw[4] = {0, 1, 0, -1};

struct Edge {
  int to;
  int weight;
  Edge(int t, int w) : to(t), weight(w) {}
};
using Graph = vector<vector<Edge>>;
using P = pair<ll, int>;

class UnionFind {
public:
  vi Parent;
  UnionFind(int n) { Parent = vi(n, -1); }

  int root(int a) {
    if (Parent[a] < 0)
      return a;
    else
      return Parent[a] = root(Parent[a]);
  }

  int size(int a) { return -Parent[root(a)]; }

  bool merge(int a, int b) {
    a = root(a);
    b = root(b);
    if (a == b)
      return false;

    if (size(a) < size(b))
      swap(a, b);
    Parent[a] += Parent[b];
    Parent[b] = a;

    return true;
  }
};

class Factrial {
public:
  vl Fac;
  Factrial(int MAX) {
    Fac = vl(MAX + 1);
    rep(i, MAX) {
      if (i == 0)
        Fac[i + 1] = 1;
      else
        Fac[i + 1] = ((i + 1) * Fac[i]) % MOD;
    }
  }
};

ll n, m, v, p;
vl a;
vl s;

bool check(int X) {
  if (X <= p - 1)
    return true;
  if (a[p - 1] - a[X] > m)
    return false;

  // 票の受け皿の数
  ll num = n * m + (X - p + 1) * a[X] - (s[X] - s[p - 1]);
  return num >= m * v;
}

int main() {
  cin >> n >> m >> v >> p;
  a.resize(n);

  rep(i, n) cin >> a[i];

  sort(all(a), greater<ll>());

  s.resize(n + 1);
  rep(i, n) s[i + 1] = s[i] + a[i];

  rrep(i, n) {
    if (check(i)) {
      cout << i + 1 << endl;
      return 0;
    }
  }
}