문제
들어가며
이 문제는 스택으로 풀 수 있다.
처음 접근은 이전에 풀었던 히스토그램처럼 접근했더니
가볍게 출력초과(시간초과)가 반겨주었다.
코드
import sys
input = sys.stdin.readline
n = int(input().strip())
towers = list(map(int, input().strip().split()))
stack = []
result = [0] * n # 결과를 저장할 리스트 초기화
for i in range(n):
# 현재 탑보다 낮은 탑은 스택에서 제거
while stack and towers[stack[-1]] < towers[i]:
stack.pop()
# 스택이 비어 있지 않다면, 가장 가까운 왼쪽의 높은 탑의 인덱스를 결과에 저장
if stack:
result[i] = stack[-1] + 1 # 0-based index를 1-based로 변환
# 현재 탑의 인덱스를 스택에 추가
stack.append(i)
# 결과 출력
print(" ".join(map(str, result)))
풀이
스택에는 현재까지 처리된 탑들의 인덱스를 저장한다.
현재 탑의 높이가 스택에 저장된 마지막 탑의 높이보다 크면, 해당 탑은 신호를 받을 수 없으므로 스택에서 제거한다.
다음과 같은 과정을 거치게 된다.
입력
5
6 9 5 7 4
탑 1 (높이: 6)
1. 현재 탑의 인덱스 : i = 0, 높이 : towers = 6
2. 스택이 비어 있으므로, 이 탑은 신호를 받을 수 있는 왼쪽 탑은 없다.
3. 결과 리스트에서 해당 위치를 바꾸지 않고 0으로 유지한다.
4. 현재 탑의 인덱스를 스택에 추가한다.
탑 2 (높이: 9)
1. 현재 탑의 인덱스: i = 1, 높이 : towers = 9
2. 스택에 값이 있고, 현재 탑보다 높이가 낮으므로 pop을 한다.
3. 스택이 비어있기 때문에, 이 탑과 신호를 받을 수 있는 왼쪽 탑은 없다.
4. 결과를 리스트에서 해당 위치를 바꾸지 않고 0으로 유지한다.
5. 현재 탑의 인덱스를 스택에 추가한다.
탑 3 (높이: 5)
1. 현재 탑의 인덱스 i = 2, 높이 : towers = 5
2. 스택에 값이 있지만, peek에 있는 값이 현재 탑보다 높으므로 pop을 하지 않는다.
3. 스택이 비어있지 않기 때문에, 이 탑과 신호를 받을 수 있는 왼쪽 탑은 존재한다.
4. peek의 인덱스를 저장한다.
5. 현재 탑의 인덱스를 스택에 추가한다.
탑 4 (높이: 7)
1. 현재 탑의 인덱스 i = 3, 높이 : 7
2. 스택에 값이 있고, peek에 있는 값이 현재 탑보다 작으므로 pop을 한다. -> 5가 사라진다.
3. 스택이 비어있지 않기 때문에, 이 탑과 신호를 받을 수 있는 왼쪽 탑은 존재한다. 그게 바로 높이 9인 index 1이다.
4. peek의 인덱스를 저장한다.
5. 현재 탑의 인덱스를 스택에 추가한다.
탑 5 (높이:4)
1. 현재 탑의 인덱스 i = 4, 높이 : 4
2. 스택에 값이 있고, peek에 있는 값이 현재 탑 높이보다 크므로 넘어간다.
3. 스택이 비어있지 않기 때문에, 이 탑과 신호를 받을 수 있는 왼쪽 탑은 존재하고, 바로 옆에 있는 peek 탑이다.
4. peek의 인덱스를 저장한다.
5. 현재 탑의 인덱스를 스택에 추가하지만, 모든 탑을 돌았으니 반복문은 종료된다.
이때, result에 들어가는 값은 0부터 시작하므로, 실제 결과에 탑의 인덱스를 넣을 땐, +1을 해준다.
'Algorithm > 백준' 카테고리의 다른 글
[백준] 1655- 가운데를 말해요 문제 풀이(자바,Java) (0) | 2025.03.25 |
---|---|
[백준] 10000 - 원 영역 문제 풀이(자바,Java) (0) | 2025.03.24 |
[백준] 6549 - 히스토그램에서 가장 큰 직사각형 문제 풀이(파이썬,Python) (0) | 2025.03.22 |
[백준]11053- 가장 긴 증가하는 부분 수열 문제 풀이(파이썬,Python) (2) | 2025.03.21 |
[백준]2470 - 두 용액 문제 풀이(파이썬,Python) (2) | 2025.03.21 |