알고리즘💻/그리디

BOJ 19639번: 배틀로얄

호프 2021. 1. 16. 03:16

www.acmicpc.net/problem/19639

 

19639번: 배틀로얄

첫 번째 줄에 X, Y, M (0 ≤ X, Y ≤ 100,000, 2 ≤ M ≤ 100,000)이 주어진다. M은 짝수다. 다음 X개의 줄에는 i번째 사람과 싸웠을 때 잃게 되는 체력이 주어진다. 이 수는 0 이상 M / 2 이하의 정수이다.

www.acmicpc.net

아이디어:

어려웡..

1. 포션은 체력이 m//2보다 같거나 작은 경우에만 섭취

2. 그러면 데미지의 합 > 초기 체력m+회복 합 인 경우를 걸러내면 불가능한 경우 걸러낼 수 있음.

3. 플레이어를 돌아가면서 데미지를 받고, 남은 체력이 m//2보다 같거나 작은 경우 체력이 m//2보다 같거나 크게 될때까지 포션 섭취. 만약 포션이 없으면 그대로 진행.

4. 플레이어를 다 돈 후 포션이 남으면 남은 포션 출력

 

생각해볼 점: 저 굵은 글씨 친 부분을 생각하지 못해서 삽질했다. 남이 짠 코드를 보면서 로직을 이해할 때는 제대로 보자.. 대충 훑지 말고^^

 

코드:

import sys
x, y, m = map(int, sys.stdin.readline().split())
damage = []
heal = []
t_damage = 0
t_heal = m
M = m//2
for i in range(x):
    a = int(sys.stdin.readline())
    damage.append([a, i+1])
    t_damage+=a
    
for i in range(y):
    a = int(sys.stdin.readline())
    heal.append([a, i+1])
    t_heal+=a

#게임에서 이길 방법이 없는 경우
if (t_damage >= t_heal):
    print(0)
    sys.exit(0)
    
#내림차순으로 정렬
damage.sort(key = lambda x:-x[0])
heal.sort(key = lambda x:-x[0])

j=0
for i in range(x):
    m -= damage[i][0]
    print(damage[i][1]*-1)
    if (m<=M and j<y):
        while(j<y):
            m+=heal[j][0]
            print(heal[j][1])
            j+=1
            if (m>M): break

if (j<y):
    for k in range(j,y, 1):
        print(heal[k][1])