코딩테스트/이진 탐색
[코테] 공유기 설치
수타.
2024. 9. 11. 12:04
https://www.acmicpc.net/problem/2110
2110번: 공유기 설치
첫째 줄에 집의 개수 N (2 ≤ N ≤ 200,000)과 공유기의 개수 C (2 ≤ C ≤ N)이 하나 이상의 빈 칸을 사이에 두고 주어진다. 둘째 줄부터 N개의 줄에는 집의 좌표를 나타내는 xi (0 ≤ xi ≤ 1,000,000,000)가
www.acmicpc.net
N개의 집의 개수에 c개의 공유기를 설치하는데 공유기간 거리를 최대로 하고싶을때 공유기간 거리중 최소치를 구하시오.
import sys
input = sys.stdin.readline
n,c =map(int,input().split())
arr = []
for _ in range(n):
arr.append(int(input()))
arr.sort()
def check(m):
temp = 0
last =arr[0]
for i in arr[1:]:
if i>=last+m:
last=i
temp+=1
if temp==c-1:
return 1
#m거리로 설치했는데 다설치했으면 가능
return 0
ans = 0
s = 1
e = (arr[-1]-arr[0])//(c-1)
while s<=e:
m = (s+e)//2
if check(m):#설치가능,더늘려보자
ans = m
s = m+1
else:#설치불가능,줄이자
e = m-1
print(ans)
오랜만에 다시 풀었는데 기억이 안나 차근차근 풀었습니다.
좌표의 범위가 10억이고 집의 범위가 20만이므로 큰 숫자들로 보아 이진탐색의 가능성을 열어두었고 공유기간 거리를 매번 설정하고 이를 집 전체를 탐색하며 가능불가능 여부를 판단한다고 했을때 시간복잡도는 20만 × log(10억)입니다.
2^10=1024이므로 log_2(10억)은 30보다 작은 수이기에 전체시간복잡도는 600만 이어서 시간제한 2초(파이썬 기준 4000만)보다 작아 해도되겠다라는 판단이 섰습니다.
제일 이상적인 배치를 e에놓고 (첫번째는 무조건 설치하기 때문에 c-1로 나누어줍니다) 이진탐색을 하며 가장 마지막 성공을 정답으로 최신화 해줍니다.
설치가능여부 확인은 맨앞에 먼저 설치했다고 가정하고(c-1), 집을 앞에서 부터 확인하며 이전 설치위치보다 m이상 거리가 있는곳에 설치를 반복하며 c개 전부 설치하면 1 전체를돌았는데도 설치를 하지 못했다면 0을 반환해 판단하였습니다.