| # | 제출 시각 | 아이디 | 문제 | 언어 | 결과 | 실행 시간 | 메모리 | 
|---|---|---|---|---|---|---|---|
| 979555 | kilkuwu | 선물상자 (IOI15_boxes) | C++17 | 0 ms | 0 KiB | 
이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include "boxes.h"
#ifdef LOCAL
#include "template/debug.hpp"
#else 
#define dbg(...) ;
#define timer(...) ;
#endif
long long delivery(int N, int K, int L, int p[]) {
  int split = std::upper_bound(p, p + N, L / 2) - p;
  int left = split;
  int right = split;
  long long ans = 0;
  while (left >= K) {
    ans += p[left - 1] * 2;
    left -= K;
  }
  while (N - right >= K) { 
    ans += (L - p[right]) * 2;
    right += K;
  }
  // now what can we do ? 
  // we can go in either direction 
  if (right == N && left == 0) return ans;
  if (right == N || left == 0) {
    if (right == N) {
      return ans + p[left - 1] * 2;
    } else {
      return ans + (L - p[right]) * 2;
    }
  }
  // both of em are non negative
  long long naive = ans + p[left - 1] * 2 + (L - p[right]) * 2;
  // that's the naieve solution
  int tot = left + N - right;
  long long round = ans + L;
  if (tot > K) {
    int left_remain = tot - K;
    int right_remain = tot - K;
    round += std::min(p[left_remain - 1], L - p[N - right_remain]) * 2;
  }
  ans += std::min(naive, round);
  return ans;
}
#ifdef LOCAL
int main() {
  int N, K, L, i;
  std::cin >> N >> K >> L;
  int *p = (int*)malloc(sizeof(int) * (unsigned int)N);
  for (i = 0; i < N; i++) {
    std::cin >> p[i];
  }
  std::cout << delivery(N, K, L, p) << "\n";
  return 0;
}
#endif
