Problem p02774 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
using namespace std;

#define IOS                                                                    \
  ios_base::sync_with_stdio(false);                                            \
  cin.tie(NULL);

#define ff first
#define ss second
#define pb push_back
#define pf push_front
#define mp make_pair
#define in insert
#define ld long double

#define TRACE
#ifdef TRACE
#define trace(...) __f(#__VA_ARGS__, __VA_ARGS__)
template <typename Arg1> void __f(const char *name, Arg1 &&arg1) {
  cerr << name << " : " << arg1 << std::endl;
}
template <typename Arg1, typename... Args>
void __f(const char *names, Arg1 &&arg1, Args &&...args) {
  const char *comma = strchr(names + 1, ',');
  cerr.write(names, comma - names) << " : " << arg1 << " | ";
  __f(comma + 1, args...);
}
#else
#define trace(...) 1
#endif
template <class T> ostream &operator<<(ostream &os, vector<T> V) {
  os << "[ ";
  for (auto v : V)
    os << v << " ";
  return os << "]";
}
template <class L, class R> ostream &operator<<(ostream &os, pair<L, R> P) {
  return os << "(" << P.first << "," << P.second << ")";
}

typedef long long int ll;

typedef vector<int> vi;
typedef vector<ll> vl;
typedef vector<vi> vvi;
typedef vector<vl> vvl;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef vector<pii> vpii;
typedef vector<pll> vpll;
const ll mod = 1e9 + 7;
const ll MAX_NODES = 200001;
const ll MAX_LOG = 50;
ll power(ll x, ll n) {
  ll res = 1;
  for (; n > 0; n >>= 1) {
    if (n & 1)
      res = (res * x) % mod;
    x = (x * x) % mod;
  }
  return res;
}

int main() {
#ifndef ONLINE_JUDGE
  freopen("input.txt", "r", stdin);
  freopen("output.txt", "w", stdout);
#endif
  IOS ll n;
  ll k;
  cin >> n >> k;
  ll a[n];
  vl pos, neg;
  ll z = 0;
  for (ll i = 0; i < n; i++) {
    cin >> a[i];
    if (a[i] > 0)
      pos.pb(a[i]);
    else if (a[i] == 0)
      z++;
    else {
      neg.pb(-a[i]);
    }
  }
  sort(pos.begin(), pos.end());
  sort(neg.begin(), neg.end());
  if (k <= (pos.size() * neg.size())) {
    ll l = -1e18, r = -1;
    ll fin = 0;
    auto check = [&](ll temp) {
      ll ans = 0;
      for (ll i = 0; i < neg.size(); i++) {
        ll pp = ((temp % neg[i])
                     ? upper_bound(pos.begin(), pos.end(), temp / neg[i])
                     : lower_bound(pos.begin(), pos.end(), temp / neg[i])) -
                pos.begin();
        ans += (pos.size() - pp);
      }
      return ans;
    };
    while (r - l > 1) {
      ll mid = (r + l) / 2;
      ll temp = -mid;
      ll ans = 0;
      ans = check(temp);
      if (ans >= k) {
        r = mid;
      } else {
        l = mid;
      }
    }
    if (check(-l) == k)
      cout << l << endl;
    else {
      cout << r << endl;
    }

    return 0;

  } else {
    k -= pos.size() * neg.size();
  }
  if (k <= (z * (n - z) + (z * (z - 1)) / 2)) {
    cout << 0 << endl;
    return 0;
  } else {
    k -= (z * (n - z) + (z * (z - 1)) / 2);
    ll l = 1, r = 1e18;
    // trace(k);
    auto check = [&](ll temp) {
      ll ans = 0;
      for (ll i = 0; i < neg.size(); i++) {
        ll pp =
            upper_bound(neg.begin(), neg.end(), temp / neg[i]) - neg.begin();
        if (pp > i)
          ans += (pp - i - 1);
      }

      for (ll i = 0; i < pos.size(); i++) {
        ll pp =
            upper_bound(pos.begin(), pos.end(), temp / pos[i]) - pos.begin();
        if (pp > i)
          ans += (pp - i - 1);
      }
      return ans;
    };
    while (r - l > 1) {
      ll mid = (r + l) / 2;
      ll temp = mid;
      ll ans = check(temp);
      if (ans >= k) {

        r = mid;
      } else {
        l = mid;
      }
    }
    if (check(l) == k)
      cout << l << endl;
    else {
      cout << r << endl;
    }

    return 0;
  }
}

Fixed submission:
#include <bits/stdc++.h>
using namespace std;

#define IOS                                                                    \
  ios_base::sync_with_stdio(false);                                            \
  cin.tie(NULL);

#define ff first
#define ss second
#define pb push_back
#define pf push_front
#define mp make_pair
#define in insert
#define ld long double

#define TRACE
#ifdef TRACE
#define trace(...) __f(#__VA_ARGS__, __VA_ARGS__)
template <typename Arg1> void __f(const char *name, Arg1 &&arg1) {
  cerr << name << " : " << arg1 << std::endl;
}
template <typename Arg1, typename... Args>
void __f(const char *names, Arg1 &&arg1, Args &&...args) {
  const char *comma = strchr(names + 1, ',');
  cerr.write(names, comma - names) << " : " << arg1 << " | ";
  __f(comma + 1, args...);
}
#else
#define trace(...) 1
#endif
template <class T> ostream &operator<<(ostream &os, vector<T> V) {
  os << "[ ";
  for (auto v : V)
    os << v << " ";
  return os << "]";
}
template <class L, class R> ostream &operator<<(ostream &os, pair<L, R> P) {
  return os << "(" << P.first << "," << P.second << ")";
}

typedef long long int ll;

typedef vector<int> vi;
typedef vector<ll> vl;
typedef vector<vi> vvi;
typedef vector<vl> vvl;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef vector<pii> vpii;
typedef vector<pll> vpll;
const ll mod = 1e9 + 7;
const ll MAX_NODES = 200001;
const ll MAX_LOG = 50;
ll power(ll x, ll n) {
  ll res = 1;
  for (; n > 0; n >>= 1) {
    if (n & 1)
      res = (res * x) % mod;
    x = (x * x) % mod;
  }
  return res;
}

int main() {

  IOS ll n;
  ll k;
  cin >> n >> k;
  ll a[n];
  vl pos, neg;
  ll z = 0;
  for (ll i = 0; i < n; i++) {
    cin >> a[i];
    if (a[i] > 0)
      pos.pb(a[i]);
    else if (a[i] == 0)
      z++;
    else {
      neg.pb(-a[i]);
    }
  }
  sort(pos.begin(), pos.end());
  sort(neg.begin(), neg.end());
  if (k <= (pos.size() * neg.size())) {
    ll l = -1e18, r = -1;
    ll fin = 0;
    auto check = [&](ll temp) {
      ll ans = 0;
      for (ll i = 0; i < neg.size(); i++) {
        ll pp = ((temp % neg[i])
                     ? upper_bound(pos.begin(), pos.end(), temp / neg[i])
                     : lower_bound(pos.begin(), pos.end(), temp / neg[i])) -
                pos.begin();
        ans += (pos.size() - pp);
      }
      return ans;
    };
    while (r - l > 1) {
      ll mid = (r + l) / 2;
      ll temp = -mid;
      ll ans = 0;
      ans = check(temp);
      if (ans >= k) {
        r = mid;
      } else {
        l = mid;
      }
    }
    if (check(-l) == k)
      cout << l << endl;
    else {
      cout << r << endl;
    }

    return 0;

  } else {
    k -= pos.size() * neg.size();
  }
  if (k <= (z * (n - z) + (z * (z - 1)) / 2)) {
    cout << 0 << endl;
    return 0;
  } else {
    k -= (z * (n - z) + (z * (z - 1)) / 2);
    ll l = 1, r = 1e18;
    // trace(k);
    auto check = [&](ll temp) {
      ll ans = 0;
      for (ll i = 0; i < neg.size(); i++) {
        ll pp =
            upper_bound(neg.begin(), neg.end(), temp / neg[i]) - neg.begin();
        if (pp > i)
          ans += (pp - i - 1);
      }

      for (ll i = 0; i < pos.size(); i++) {
        ll pp =
            upper_bound(pos.begin(), pos.end(), temp / pos[i]) - pos.begin();
        if (pp > i)
          ans += (pp - i - 1);
      }
      return ans;
    };
    while (r - l > 1) {
      ll mid = (r + l) / 2;
      ll temp = mid;
      ll ans = check(temp);
      if (ans >= k) {

        r = mid;
      } else {
        l = mid;
      }
    }
    if (check(l) == k)
      cout << l << endl;
    else {
      cout << r << endl;
    }

    return 0;
  }
}