Algorithm/Programmers
[프로그래머스/Python] 스택/큐
빵빵0
2023. 9. 5. 01:37
import math
def solution(progresses, speeds):
answer = []
works = [] # 작업 시간 배열
for i in range(len(progresses)):
work = math.ceil((100 - progresses[i]) / speeds[i])
works.append(work)
big = works[0] # 가장 긴 작업 시간
cnt = 1
for i in range(1, len(progresses)):
if works[i] <= big:
cnt += 1
else:
answer.append(cnt)
big = works[i]
cnt = 1
answer.append(cnt) # 마지막 배포
return answer
자꾸 테스트 케이스 몇 개가 틀려서 반례를 찾았다.
works = [5, 3, 4] 일 경우 답은 [3] 인데, 예전 내 코드는 바로 전 일수랑만 비교해서 [1, 2] 라는 답이 나왔던 것이다!
big은 가장 긴 작업 시간이고, 그 이하의 숫자는 얼마든지 커버(?)할 수 있다!!!
고로 big보다 짧은 작업들은 다 big과 함께 배포되고(if문), big보다 큰 숫자가 나타다면 비로소 새 배포를 시작하게 되는 것이다(else문).
그리고 마지막 배포도 잊지말고 append 해주자!
+) 다른 사람의 풀이
from math import ceil
def solution(progresses, speeds):
daysLeft = list(map(lambda x: (ceil((100 - progresses[x]) / speeds[x])), range(len(progresses))))
count = 1
retList = []
for i in range(len(daysLeft)):
try:
if daysLeft[i] < daysLeft[i + 1]:
retList.append(count)
count = 1
else:
daysLeft[i + 1] = daysLeft[i]
count += 1
except IndexError:
retList.append(count)
return retList
try, catch 로 처리한게 참신했다.
big을 설정하지 않고, 가장 큰 값으로 계속 다음 수를 덮어씌웠다.
그러면 간결하게 위 코드처럼 비교가 가능하다.
def solution(progresses, speeds):
Q=[]
for p, s in zip(progresses, speeds):
if len(Q)==0 or Q[-1][0]<-((p-100)//s):
Q.append([-((p-100)//s),1])
else:
Q[-1][1]+=1
return [q[1] for q in Q]
zip이 있다는걸 잊고 있었다!
작업 일수를 계산할 때, 음수(-)로 몫을 구한 다음 다시 양수로 바꿔줬는데 `math.ceil()` 한 것과 동일하다! (내림한 음수, 음수에서 내림은 절댓값 커짐)
Q에 넣어주는 것은 작업 일수와 count(배포 가능한 기능 수)
뒷 작업은 앞 작업의 작업 일수와 비교해서 작으면 앞 작업 count에 +1, 크면 새로 원소를 추가한다
count 부분만 잘라서 답 리턴