문제 설명
어떤 숫자에서 k개의 수를 제거했을 때 얻을 수 있는 가장 큰 숫자를 구하려 합니다.
예를 들어, 숫자 1924에서 수 두 개를 제거하면 [19, 12, 14, 92, 94, 24] 를 만들 수 있습니다. 이 중 가장 큰 숫자는 94 입니다.
문자열 형식으로 숫자 number와 제거할 수의 개수 k가 solution 함수의 매개변수로 주어집니다. number에서 k 개의 수를 제거했을 때 만들 수 있는 수 중 가장 큰 숫자를 문자열 형태로 return 하도록 solution 함수를 완성하세요.
제한사항
- number는 2자리 이상, 1,000,000자리 이하인 숫자입니다.
- k는 1 이상 number의 자릿수 미만인 자연수입니다
입출력 예
지금 담으려고 하는 것보다 작은 것
이 나오면 뺀다.k개까지만
이 과정을 반복한다.O(n)
-> 더해지는 것도 빠지는 것도 모두 한 번이기 때문에 탐욕법
에 의한 알고리즘을 사용할 수 있는가?앞 단계에서의 선택(앞자리에 큰 수)
이 이후 단계에서의 동작에 의한 해의 최적성
에 영향을 주지 않는다.stack
을 이용해서 number
의 원소를 쌓는다. stack의 마지막 원소
가 비교하는 값보다 작고, 횟수가 k
번을 초과하지 않은 경우 k
횟수를 1 회 줄이고 stack
의 마지막 값을 pop
으로 꺼내 제거한다.리스트 슬라이싱
하여 처리해 준다.def solution(number, k):
answer = ''
stack = []
for num in number:
while stack and stack[-1] < num and k > 0:
k -= 1
stack.pop()
stack.append(num)
if k != 0:
stack = stack[:-k]
answer = ''.join(stack)
return answer
for 문
에서 index
역시 같이 체크하게 만들어 주었고 k 번
제거를 끝낸 경우 collected에 확인하지 않은 index
이후의 값을 추가해 주고 for문
을 빠져나가게 처리해 주었다.while
과 for
같은 반복문에서는 모든 행위가 끝났을 때 의미 없는 반복을 하지 않도록 처리해 주는 게 시간적 효율을 따졌을 때 유리하다.def solution(number, k):
collected = []
for i, num in enumerate(number):
#아직까지 k>0 빼낼 개수가 남아 있으면서 마지막 글자가 num보다 작은 거로 비교해야 하지만
#이때 collected 배열에 원소가 없다면 오류가 발생함으로 이 부분도 처리해 줌.
while len(collected) > 0 and collected[-1] < num and k > 0:
collected.pop()
k -= 1
if k == 0:
collected += list(number[i:])
break
collected.append(num)
collected = collected[:-k] if k > 0 else collected
answer = ''.join(collected)
return answer