문제
수열 A가 주어졌을 때, 가장 긴 증가하는 부분 수열을 구하는 프로그램을 작성하시오.
예를 들어, 수열 A = {10, 20, 10, 30, 20, 50} 인 경우에 가장 긴 증가하는 부분 수열은 A = {10, 20, 10, 30, 20, 50} 이고, 길이는 4이다.
입력
첫째 줄에 수열 A의 크기 N (1 ≤ N ≤ 1,000)이 주어진다.
둘째 줄에는 수열 A를 이루고 있는 Ai가 주어진다. (1 ≤ Ai ≤ 1,000)
출력
첫째 줄에 수열 A의 가장 긴 증가하는 부분 수열의 길이를 출력한다.
예제 입력 1 복사
6
10 20 10 30 20 50
예제 출력 1 복사
4
처음에 이문제는 그냥 중복 제거후 오름차순으로 구현했었다.
하지만 이 문제의 가장 큰 문제는 증가된 부분 수열이고 이게 이 문제의 가장 큰 힌트였다.
즉, 이 문제는
1. 리스트 내 하나의 수를 기준으로 잡고 그 뒤에 나오는 값들을 비교하면서 오름차순으로 증가되는 수열을 찾는 것이다. 그래서 만약 주어진 값이 [5,1,6,2,7,3,8] 이렇게 있으면
2. '5'을 기준으로 증가된 수열을 찾는다면 [5,6,7,8] 이 나올 것이고, '1'을 기준으로 잡는다면 [1,2,3] 나올 것이다.
3. 하지만 이렇게 구현한다면 단점이 생긴다.
만약 주어진 값이 [1,3,4,2,3,4] 일 경우 '1'을 기준으로 잡는다면 [1,3,4] 와 [1,2,3,4]가 나올 것이다.
4. 그래서 이 문제는 DP를 사용해서 풀어야 겠다고 생각을 했고 DP문제는 거의 max(), min()이 나오기 때문에 코드를 작성했다.
-> DP문제는 이전에 계산된 값을 재사용해서 해결하는 방식이고 나는 상향식 접근법을 이용해 for문으로 구현했다. 그러기 위해서는 결과를 저장하는 TABLE이 필요하다. 이걸 나는 dp라는 리스트를 만들었다.
5. 기준을 잡은 숫자와 그 이전의 숫자의 DP 배열의 값을 비교하여 문제를 풀면된다.
n = int(input())
a = list(map(int, input().split()))
dp = [0] * n
for i in range(n):
for j in range(i):
if a[i] > a[j] and dp[i] < dp[j]:
dp[i] = dp[j]
dp[i] += 1
print(max(dp))
코드 설명
입력값 : n = 6
입력값 : a = [10, 20, 10, 30, 20, 50]
dp = 초기값 : [0, 0, 0, 0, 0, 0, 0]
for문을 다 돌고 난 뒤 : [1, 2, 1, 3, 2, 4]
1. dp 라는 이름의 리스트를 만들고 0으로 초기화를 한다. => dp = [0,0,0,0,0,0]
2. 첫번째 for문으러 값을 지정해준다 .
3. 두번째 for문으로 지정한 값을 이전값들과 비교해준다.
4. if 문에서 a[i] > a[j]는 지정한 값이 이전 값보다 커야하고 dp[i] < dp[j]는 현재 값이 이전 값보다 작으면 현재 dp리스트에 이전 dp 값을 지정한다.
5. for문이 다 돌면 dp[i]에는 0 또는 i 이전의 j 중 dp 값이 큰 dp[j]의 값이 들어 있을 것이다.
6. 그리고 dp[i]에 1을 더해주고
7. dp값중 가장 큰 값을 출력해준다.
3번 과정의 자새한 풀이
# i = 0일 때 , a[0] = 10, dp = [1, 0, 0, 0, 0, 0]
# i = 1 , a[1] = 20, a[1] > a[0] 이고 dp[1] < dp[0] 이므로 dp = [1, 2, 0, 0, 0, 0]
# i = 2 , a[2] = 10, a[2] > a[0] 은 거짓이므로 dp = [1, 2, 1, 0, 0, 0]
# i = 3,
.
.
.
이렇게 풀면 결국에 dp = [1, 2, 1, 3, 2, 4이 남게 될 것이고 이 중 가장 큰 값을 출력해주면 된다.
'CodingTest > [Baekjoon Online Judge]' 카테고리의 다른 글
1260 DFS와 BFS : Python (2) | 2024.10.26 |
---|---|
7568 덩치 - 파이썬 (0) | 2024.03.12 |
4673 셀프넘버 - 파이썬 (0) | 2024.03.11 |
백준 1157번 [파이썬] 단어 공부 (0) | 2023.04.13 |
백준 10988번 [파이썬] 팰린드롬인지 확인하기 (0) | 2023.03.31 |