목차
🖇️ 링크
https://www.acmicpc.net/problem/1365
🗒️ 파이썬 코드 풀이
from bisect import bisect_left
N = int(input())
lst = list(map(int,input().split()))
lis = [0]
for i in range(len(lst)):
if lis[-1] < lst[i]:
lis.append(lst[i])
else:
v = bisect_left(lis,lst[i])
lis[v] = lst[i]
print(N-(len(lis)-1))
1. 문제를 보고 LIS (Longest Increasing Sequence) 문제임을 알아야한다.
처음 풀면, 생각할 수 없을 것 같다... 그냥 문제를 몇번 풀고 익숙해져야 될듯
2. 문제의 조건은 전봇대의 개수 N(1 ≤ N ≤ 100,000) 이다.
- 때문에 시간복잡도가 O(N^2) 이하여야 함
- 이중 for 문이 안되기 떄문에, 이분탐색으로 접근
3. 이제 조건에 맞게 lis 리스트를 오름차순으로 채워주면 된다.
- lis 리스트의 가장 오른쪽에 있는 값이 가장 큰 값
- 가장 오른쪽의 값보다 큰 경우
- lis의 맨 앞 부분에 넣어줌
- 작거나 같은 경우
- 이분탐색으로 교체해줄 위치 찾고 교체
📌 문제 코멘트
![](https://blog.kakaocdn.net/dn/bZq8JY/btsMgOMSJ10/eoeL8hW3jZHgQKzSwaR5gK/img.png)
N = int(input())
lst = list(map(int,input().split()))
lis = [0]
for i in range(len(lst)):
if lis[-1] < lst[i]:
lis.append(lst[i])
else:
for k in range(len(lis)-1):
if lis[k] <= lst[i] < lis[k+1]:
lis[k+1] = lst[i]
break
print(N-(len(lis)-1))
- 보통 LIS 알고리즘 방식이다.
- 이중 for문으로 LIS 문제를 해결한다.
- 시간 복잡도는 O(N^2)으로 계산된다.
- 이렇게하면 시간 초과가 발생한다.
- 그래서 해당 문제는 O(NlogN)의 시간 복잡도를 가지게 이분 탐색을 한다.
- 가장 헷갈렸던 부분은, 이렇게 막무가내로 값을 교체해도 되는지였다.
- 길이 K의 증가 부분 수열은 K개의 위치가 항상 존재
- 더 작은 값의 교체로 증가 수열의 원소 선택지를 넓혀줌
문제의 로직만 알고 있으면, 구현자체는 막 어렵거나 하지 않다.
📚문제
공화국에 있는 유스타운 시에서는 길을 사이에 두고 전봇대가 아래와 같이 두 줄로 늘어서 있다. 그리고 길 왼편과 길 오른편의 전봇대는 하나의 전선으로 연결되어 있다. 어떤 전봇대도 두 개 이상의 다른 전봇대와 연결되어 있지는 않다.
![](https://blog.kakaocdn.net/dn/cCal4j/btsMhPRMmh9/cstMLAMLqVgf6IoQcFX1J0/img.jpg)
문제는 이 두 전봇대 사이에 있는 전깃줄이 매우 꼬여 있다는 점이다. 꼬여있는 전깃줄은 화재를 유발할 가능성이 있기 때문에 유스타운 시의 시장 임한수는 전격적으로 이 문제를 해결하기로 했다.
임한수는 꼬여 있는 전깃줄 중 몇 개를 적절히 잘라 내어 이 문제를 해결하기로 했다. 하지만 이미 설치해 놓은 전선이 아깝기 때문에 잘라내는 전선을 최소로 하여 꼬여 있는 전선이 하나도 없게 만들려고 한다.
유스타운 시의 시장 임한수를 도와 잘라내야 할 전선의 최소 개수를 구하는 프로그램을 작성하시오.
입력
첫 줄에 전봇대의 개수 N(1 ≤ N ≤ 100,000)이 주어지고, 이어서 N보다 작거나 같은 자연수가 N개 주어진다. i번째 줄에 입력되는 자연수는 길 왼쪽에 i번째 전봇대와 연결된 길 오른편의 전봇대가 몇 번 전봇대인지를 나타낸다.
출력
전선이 꼬이지 않으려면 최소 몇 개의 전선을 잘라내야 하는 지를 첫째 줄에 출력한다.
예제 입력 1 복사
4
2 3 4 1
예제 출력 1 복사
1
'♟️ 알고리즘 > 알고리즘_백준' 카테고리의 다른 글
[Python][백준] 2170. 선 긋기/ 정렬,스위핑 (G5) (0) | 2025.02.07 |
---|---|
[Python][백준] 1700. 멀티탭 스케줄링 / 그리디 (G1) (0) | 2025.01.29 |
[Python][백준] 2252. 줄 세우기 / 위상정렬, DAG (G3) (0) | 2025.01.28 |
[Python][백준] 1916. 최소비용 구하기/ 다익스트라, 최단 경로 (G5) (0) | 2025.01.27 |
[Python][백준] 1062. 가르침 / 브루트포스,비트마스킹,백트래킹 (G4) (0) | 2025.01.26 |