# | 제출 시각 | 아이디 | 문제 | 언어 | 결과 | 실행 시간 | 메모리 |
---|---|---|---|---|---|---|---|
290336 | A02 | 커다란 상품 (IOI17_prize) | C++14 | 0 ms | 0 KiB |
이 제출은 이전 버전의 oj.uz에서 채점하였습니다. 현재는 제출 당시와는 다른 서버에서 채점을 하기 때문에, 다시 제출하면 결과가 달라질 수도 있습니다.
#include <bits/stdc++.h>
#include "prize.h"
using namespace std;
vector<vector<int> > asked;
vector<int> ask2(int i){
if (asked[i][0] == -1){
asked[i] = ask(i);
}
return asked[i];
}
int find_best(int n) {
asked = vector<vector<int> > (n, vector<int> (2, -1));
// if (n <= 5000){
// for (int i = 0; i < n; i++){
// vector<int> r = ask(i);
// if (r[0] == 0 && r[1] == 0){
// return i;
// }
// }
// }
int small_count = 0;
// for (int i = 0; i < 500; i++){
// int low = 0;
// int high = n;
// for (int a = 0; a < 9; a++){
// small_count = max(small_count, ask2((low + high) / 2)[0] + ask2((low + high) / 2)[1]);
// if (i & (1 << a)){
// cout << i << ' ' << (1 << a) << endl;
// low = (low + high) / 2;
// } else {
// high = (low + high) / 2;
// }
// }
// }
for (int i = 0; i < min(n, 500); i++){
small_count = max(small_count, ask2((low + high) / 2)[0] + ask2((low + high) / 2)[1]);
}
vector<int> small_pos (small_count, -1);
//cout << small_count << endl;
for (int p = 0; p < small_count; p++){
//cout << endl;
//cout << 'p' << ' ' << p << endl;
int low = 0;
int high = n;
int left_elements = 0;
//pth small element in [0, n).
while (high != low + 1){
int mid = (low + high) / 2;
//cout << low << ' ' << high << ' ' << left_elements << endl;
while(ask2(mid)[0] + ask2(mid)[1] != small_count && mid - 1 >= low){
mid--;
}
int m_original = (low + high) / 2;
if (m_original != mid){
//cout << 'a' << endl;
if (ask2(mid)[0] + ask2(mid)[1] != small_count){
//cout << 'b' << endl;
int width = m_original - low;
if (p <= left_elements + width){
high = m_original;
} else {
low = m_original;
left_elements += width;
}
} else {
//cout << 'c' << endl;
//cout << mid << ' ' << m_original << endl;
int extra = m_original - mid;
int left_of_mid_elements = ask2(mid)[0] + extra - 1;
//cout << ' ' << left_of_mid_elements << endl;
if (left_of_mid_elements > p){
high = m_original;
} else {
low = m_original;
left_elements = left_of_mid_elements;
}
}
} else {
int left_of_mid_elements = ask2(mid)[0];
if (left_of_mid_elements > p){
high = mid;
} else {
low = mid;
left_elements = left_of_mid_elements;
}
}
}
small_pos[p] = low;
//cout << p << ' ' << low << endl;
if (ask2(low)[0] + ask2(low)[1] == 0){
return low;
}
}
}