Problem p02774 (C++)

Buggy submission (status: Runtime Error):
// AtCoder.cpp : このファイルには 'main'
// 関数が含まれています。プログラム実行の開始と終了がそこで行われます。
//

// AtCoder.cpp : このファイルには 'main'
// 関数が含まれています。プログラム実行の開始と終了がそこで行われます。
//

#define _USE_MATH_DEFINES
#include <math.h>

// #include<cmath>

#include <algorithm>
#include <array>
#include <assert.h>
#include <bitset>
#include <chrono>
#include <cmath>
#include <deque>
#include <functional>
#include <iomanip>
#include <iostream>
#include <iterator>
#include <map>
#include <memory>
#include <queue>
#include <random>
#include <set>
#include <stack>
#include <string>
#include <tuple>
#include <unordered_set>
#include <vector>

// #include "Ants.h"
using namespace std;
typedef long long ll;
#define rad_to_deg(rad) (((rad) / 2 / M_PI) * 360)
#define EPS (1e-7)
#define INF (1e9)
#define PI (acos(-1))
#define rep(i, n) for (int i = 0; i < n; i++)
#define show(s) cout << s << endl
#define chmin(x, y) x = min(x, y)
#define chmax(x, y) x = max(x, y)
#define LINF (1000000000000000000ll)

// typedef pair < int, int> P;
ll gcd(ll a, ll b) { // 最大公約数を求める///最大公倍数a*b/gcd(a,b)
  if (b == 0)
    return a;
  return gcd(b, a % b);
}

ll lcd(ll a, ll b) { // 最小公倍数を求める　b=0のときaを返す
  if (b == 0)
    return a;
  return (a / gcd(a, b)) * b;
}
vector<int> divnum(ll num) {
  int dig;
  vector<int> p;
  while (num) {
    dig = num % 10;
    p.push_back(dig);
    num /= 10;
  }
  return p;
}
int keta(ll num) {
  int dig;
  vector<int> p;
  while (num) {
    dig = num % 10;
    p.push_back(dig);
    num /= 10;
  }
  return p.size();
}

ll N, K, A[100000];
int main() {
  cin >> N >> K;
  rep(i, N) { cin >> A[i]; }
  sort(A, A + N);

  ll ub = LINF, lb = -LINF;
  while (ub - lb > 1) {
    ll x = (ub + lb) / 2;
    // x = -7;
    bool ok = [&] {
      ll res = 0;

      rep(i, N) {
        ll l = -1, r = N;

        if (A[i] >= 0) {

          while (r - l > 1) {
            ll mid = (l + r) / 2;
            if (A[i] * A[mid] < x) {
              l = mid; // use this
            } else {
              r = mid;
            }
          }
          res += r;

        } else {
          while (r - l > 1) {
            ll mid = (l + r) / 2;
            if (A[i] * A[mid] >= x) {
              l = mid;
            } else {
              r = mid;
            }
          }
          res += (N - r);
        }
        if (A[i] * A[i] < x)
          res--;
      }
      res /= 2;
      if (res < K) {
        return true;
      } else {
        return false;
      }
    }();
    /// break;
    if (ok) {
      lb = x;
    } else {
      ub = x;
    }
  }
  cout << lb << endl;
}

Fixed submission:
// AtCoder.cpp : このファイルには 'main'
// 関数が含まれています。プログラム実行の開始と終了がそこで行われます。
//

// AtCoder.cpp : このファイルには 'main'
// 関数が含まれています。プログラム実行の開始と終了がそこで行われます。
//

#define _USE_MATH_DEFINES
#include <math.h>

// #include<cmath>

#include <algorithm>
#include <array>
#include <assert.h>
#include <bitset>
#include <chrono>
#include <cmath>
#include <deque>
#include <functional>
#include <iomanip>
#include <iostream>
#include <iterator>
#include <map>
#include <memory>
#include <queue>
#include <random>
#include <set>
#include <stack>
#include <string>
#include <tuple>
#include <unordered_set>
#include <vector>

// #include "Ants.h"
using namespace std;
typedef long long ll;
#define rad_to_deg(rad) (((rad) / 2 / M_PI) * 360)
#define EPS (1e-7)
#define INF (1e9)
#define PI (acos(-1))
#define rep(i, n) for (int i = 0; i < n; i++)
#define show(s) cout << s << endl
#define chmin(x, y) x = min(x, y)
#define chmax(x, y) x = max(x, y)
#define LINF (1000000000000000000ll)

// typedef pair < int, int> P;
ll gcd(ll a, ll b) { // 最大公約数を求める///最大公倍数a*b/gcd(a,b)
  if (b == 0)
    return a;
  return gcd(b, a % b);
}

ll lcd(ll a, ll b) { // 最小公倍数を求める　b=0のときaを返す
  if (b == 0)
    return a;
  return (a / gcd(a, b)) * b;
}
vector<int> divnum(ll num) {
  int dig;
  vector<int> p;
  while (num) {
    dig = num % 10;
    p.push_back(dig);
    num /= 10;
  }
  return p;
}
int keta(ll num) {
  int dig;
  vector<int> p;
  while (num) {
    dig = num % 10;
    p.push_back(dig);
    num /= 10;
  }
  return p.size();
}

ll N, K, A[200005];
int main() {
  cin >> N >> K;
  rep(i, N) { cin >> A[i]; }
  sort(A, A + N);

  ll ub = LINF, lb = -LINF;
  while (ub - lb > 1) {
    ll x = (ub + lb) / 2;
    // x = -7;
    bool ok = [&] {
      ll res = 0;

      rep(i, N) {
        ll l = -1, r = N;

        if (A[i] >= 0) {

          while (r - l > 1) {
            ll mid = (l + r) / 2;
            if (A[i] * A[mid] < x) {
              l = mid; // use this
            } else {
              r = mid;
            }
          }
          res += r;

        } else {
          while (r - l > 1) {
            ll mid = (l + r) / 2;
            if (A[i] * A[mid] >= x) {
              l = mid;
            } else {
              r = mid;
            }
          }
          res += (N - r);
        }
        if (A[i] * A[i] < x)
          res--;
      }
      res /= 2;
      if (res < K) {
        return true;
      } else {
        return false;
      }
    }();
    /// break;
    if (ok) {
      lb = x;
    } else {
      ub = x;
    }
  }
  cout << lb << endl;
}