Problem p00523 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <algorithm>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <list>
#include <map>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <utility>
#include <vector>

using namespace std;

#define ALL(c) c.begin(), c.end()
#define RALL(c) c.rbegin(), c.rend()
#define SORT(x) sort((x).begin(), (x).end())
#define REP(i, x, y) for (int i = (x); i < (y); ++i)
#define MP(a, b) make_pair((a), (b))
#define F_ first
#define S_ second
#define debug(x) #x << "=" << (x)

#ifdef DEBUG
#define dump(x) std::cerr << debug(x) << " (L:" << __LINE__ << ")" << std::endl
#else
#define dump(x)
#endif

typedef long long int lli;
typedef pair<int, int> pii;

const int INF = 1 << 30;
const long long int INF_ = 1LL << 58;
const double EPS = 1e-9;
const int dx[] = {1, 0, -1, 0}, dy[] = {0, 1, 0, -1};

template <typename T> ostream &operator<<(ostream &os, const vector<T> &vec) {
  os << "[";
  for (const auto &v : vec) {
    os << v << ",";
  }
  os << "]";
  return os;
}

int CalcMid(int lb, int ub, int size) {
  int mid;
  if (lb < ub)
    mid = (ub + lb) / 2;
  else
    mid = (lb + ub + size) / 2;
  mid %= size;
  return mid;
}

bool Sub_Check(int last, int mid, lli m, const vector<lli> &a) {
  lli d;
  if (last < mid) {
    if (last > 0)
      d = a[mid] - a[last - 1];
    else
      d = a[mid];
  } else if (last > mid) {
    if (last > 0)
      d = a[a.size() - 1] - a[last - 1] + a[mid];
    else
      d = a[last];
  } else {
    if (last > 0)
      d = a[last] - a[last - 1];
    else
      d = a[last];
  }
  return d >= m;
}

bool Check(const vector<lli> &a, lli m) {
  REP(i, 0, a.size()) {
    int cnt = 0, last = i;
    REP(i, 0, 3) {
      int lb = last, ub = last - 1;
      if (ub < 0)
        ub = a.size() - 1;
      do {
        int mid = CalcMid(lb, ub, a.size());
        if (Sub_Check(last, mid, m, a))
          ub = mid;
        else
          lb = mid;
      } while (abs(ub - lb) > 1 && !(lb == a.size() - 1 && ub == 0));
      if (Sub_Check(last, lb, m, a))
        ub = lb;
      if (last <= ub)
        cnt += ub - last + 1;
      else
        cnt += ub + a.size() - last + 1;
      if (!(cnt <= a.size()))
        break;
      last = (ub + 1) % a.size();
    }
    if (cnt <= a.size())
      return true;
  }
  return false;
}

int main() {
  std::ios::sync_with_stdio(false);
  std::cin.tie(0);
  int N;
  cin >> N;
  vector<lli> A(N);
  REP(i, 0, N) {
    int a;
    cin >> a;
    if (i == 0)
      A[i] = a;
    else
      A[i] = A[i - 1] + a;
  }
  lli lb = 0, ub = INF_;
  while (ub - lb > 1) {
    lli mid = (lb + ub) / 2;
    if (Check(A, mid))
      lb = mid;
    else
      ub = mid;
  }
  cout << lb << endl;
  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <list>
#include <map>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <utility>
#include <vector>

using namespace std;

#define ALL(c) c.begin(), c.end()
#define RALL(c) c.rbegin(), c.rend()
#define SORT(x) sort((x).begin(), (x).end())
#define REP(i, x, y) for (int i = (x); i < (y); ++i)
#define MP(a, b) make_pair((a), (b))
#define F_ first
#define S_ second
#define debug(x) #x << "=" << (x)

#ifdef DEBUG
#define dump(x) std::cerr << debug(x) << " (L:" << __LINE__ << ")" << std::endl
#else
#define dump(x)
#endif

typedef long long int lli;
typedef pair<int, int> pii;

const int INF = 1 << 30;
const long long int INF_ = 1LL << 58;
const double EPS = 1e-9;
const int dx[] = {1, 0, -1, 0}, dy[] = {0, 1, 0, -1};

template <typename T> ostream &operator<<(ostream &os, const vector<T> &vec) {
  os << "[";
  for (const auto &v : vec) {
    os << v << ",";
  }
  os << "]";
  return os;
}

bool Check(const vector<int> &a, lli m) {
  REP(i, 0, a.size()) {
    int cnt = 0, last = i;
    REP(i, 0, 3) {
      int crt = last;
      lli d = a[crt];
      ++cnt;
      while (cnt <= a.size() && d < m) {
        crt = (crt + 1) % a.size();
        d += a[crt];
        ++cnt;
      }
      if (!(cnt <= a.size()))
        break;
      last = (crt + 1) % a.size();
    }
    if (cnt <= a.size())
      return true;
  }
  return false;
}

int main() {
  std::ios::sync_with_stdio(false);
  std::cin.tie(0);
  int N;
  cin >> N;
  vector<int> A(N);
  REP(i, 0, N) cin >> A[i];
  lli lb = 0, ub = INF_;
  while (ub - lb > 1) {
    lli mid = (lb + ub) / 2;
    if (Check(A, mid)) {
      lb = mid;
    } else
      ub = mid;
  }
  cout << lb << endl;
  return 0;
}