본문 바로가기
알고리즘 & PS

[프로그래머스] 과제 진행하기 (Lv 2)

by 다람이도토리 2024. 10. 16.

 

https://school.programmers.co.kr/learn/courses/30/lessons/176962#

 

프로그래머스

코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.

programmers.co.kr

 

Idea/Tip.

기본적으로 스택을 이용한다. 단, 스택에서 뺄지 안 뺄지를 시간을 통해 결정해야 한다.

이를 위해 현재 시간을 계산하는 변수를 이용해야 한다. 다음 과제가 오기까지 충분한 시간이 있을 경우, 남은 과제를 한다.

과제는 없는데 시간이 더 남으면, "다음 과제 시간으로" 바로 넘어가야 한다. 아니어도 그 시간을 간다.

즉, 다음 과제 전까지의 과제 처리 여부와 상관없이 현재 시간만 조절해주면 문제 없이 예외 처리 된다.

def solution(plans):
    answer = []
    work_list = []
    # idea
    # 1. 현재 시간을 잡는다.
    # 2. 새로운 과제가 들어오려고 할 때, 현재 시간과 비교를 한다.
    # 2-1. 새로운 과제까지 시간 여유가 있을 때, 잔여 과제를 처리한다.
    # 2-2. 시간 여유가 없을 경우, 한 만큼만 처리하고, 다음 과제를 받는다.
    # 2 Tip : 즉, 시간의 체크는 새로운 과제가 "들어오려고 한 시점에 진행"
    # 마지막에 남은 과목들을 비워 처리한다.
    
    plans.sort(key = lambda x: x[1])
    # 계산 편의를 위한 사전 작업
    for p in plans:  
        p[2] = int(p[2])
        
    cur_h, cur_m = int(plans[0][1].split(":")[0]), int(plans[0][1].split(":")[1])
    
    for i in range(len(plans)):
        # 다음 계획을 정의한다.
        next_plan = plans[i]
        # 최초 항에 대한 처리
        if i == 0:
            work_list.append(next_plan)
        # 이후 항에 대한 처리
        else:
            next_h, next_m = int(next_plan[1].split(":")[0]), int(next_plan[1].split(":")[1])
            while len(work_list) > 0:
                cur_work = work_list[-1]
                # 다음 과제 전에 이번 과제를 끝낼 시간이 충분하다면
                if 60*cur_h + cur_m + int(cur_work[2]) <= 60*next_h + next_m:
                    answer.append(cur_work[0])
                    cur_m += int(cur_work[2])
                    while cur_m >= 60:
                        cur_m -= 60
                        cur_h += 1
                    work_list.pop()
                # 과제는 있는데 시간이 부족하다면, 시간을 깎는다.
                else:
                    do_time = 60*next_h + next_m - (60*cur_h + cur_m)
                    cur_work[2] -= do_time
                    cur_h, cur_m = next_h, next_m
                    break
            work_list.append(next_plan)
            cur_h, cur_m = int(next_plan[1].split(":")[0]), int(next_plan[1].split(":")[1])
    while len(work_list) > 0:
        answer.append(work_list[-1][0])
        work_list.pop()
    return answer