들어가기 전에
문제를 해결하기 위해 어떤 생각을 했는지 기록하기 위해 쓰는 글입니다.
O(10^8)의 계산을 1초라 가정했습니다.
잘못되거나 개선이 필요한 부분 지적은 언제나 환영입니다!
지문 해석
레벨을 올릴 수 있는 총합 K를 적절히 배분해서 얻을 수 있는 가장 높은 최솟값 T를 찾아야 한다.
브루트 포스로 해결한다면 최악의 경우
O(1,000,000 * 1,000,000,000) = O(10^15) 로 시간 초과를 받는다.
이분 탐색으로 해결한다면
O(1,000,000 * log(1,000,000,000)) O(1,000,000 * 29.8) = O(29,800,000) 로 해결할 수 있다.
이분탐색 범위 지정
N = 2 이고 X = {10, 10}, K = 1이라면, T의 값은 어떠한 경우에도 10이 된다.
N = 1 이고 X = {10}, K = X라면, T의 최대 값은 10 + X가 된다.
따라서, 답이 될 수 있는 T의 범위는 min(X) <= T <= min(X) + (K / N)가 된다.
이제 이 값을 중심으로 중간 값을 구해
이 중간 값보다 작은 Xi들이 중간 값이 되기 위해 필요한 값들의 합이
K보다 작거나 같은 경우를 확인하면 된다.
+++++
재채점 후 틀렸다는 결과가 나와서 뭔가 했었는데
지문에서 헷갈릴만한 점이 있었다.
처음엔 최대 팀 목표레벨 T를 구하라 한 뒤, 그 다음 줄엔 최소 T를 얻을 수 있단 식으로
T가 될 수 있는 가장 작은 값을 출력하란 걸로 착각했다.
기존 풀이를 보면 여기에 낚인 풀이가 좀 있다.
ex)
1 1000000000
1
answer : 1000000001
wrong : 1
코드
from bisect import bisect_left
N, K = map(int, input().split())
X = [int(input()) for _ in range(N)]
X.sort()
answer = 0
left, right = min(X), max(X) + K // N
while left <= right:
mid = (left + right) // 2
index = bisect_left(X, mid)
total = 0
for i in range(index):
total += mid - X[i]
if total <= K:
answer = mid
left = mid + 1
else:
right = mid - 1
print(answer)
'알고리즘 > 백준' 카테고리의 다른 글
백준 [1090] 체커(Python3) (0) | 2022.07.30 |
---|---|
백준 [13913] 숨바꼭질4(Python3) (0) | 2022.06.21 |
백준 [1045] 도로 (0) | 2022.02.23 |
백준 [16297] Eating Everything Efficiently (0) | 2022.02.23 |
백준 [2637] 장난감 조립(JAVA) (0) | 2022.02.10 |