728x90
1509. 팰린드롬 분할
난이도 : 골드 1
소요 시간 : 40분
날짜 : 2024.12.25
언어 : 파이썬
알고리즘 유형 : dp
설명 보기전에 문제 풀어보러 가기
1. 문제 설명
- 문자열이 주어진다 (길이 <= 2500)
- 문자열을 팰린드롬으로 분할한다.
- 분할 개수의 최솟값을 구한다.
2. 해결 방식
- dp를 두개 활용했다.
- 팰린드롬 dp : dp_pldm[i][j] = i인덱스부터 j인덱스까지 팰린드롬인가?의 여부
- 길이 1, 길이 2인 팰린드롬을 먼저 저장한다.
- 길이 3이상인 경우 dp 알고리즘을 활용한다. -> 시작, 끝이 같고, 내부가 팰린드롬이면 팰린드롬
- 이렇게 하면 모든 경우의 수를 찾을 수 있음.
- 분할수 dp : dp_res[i] = 0번 부터 i번 까지 팰린드롬 최소 분할 수
- dp값을 모두 0으로 해준다.
- 끝점(j)의 인덱스를 0부터 문자열의 길이까지 탐색한다.
- 시작점(i)은 0 부터 끝점 인덱스까지 탐색
- i~j가 팰린드롬인 경우에만 값을 갱신, 이 경우에 이미 존재하는 dp 값이 i-1번째의 dp값보다 같거나 작으면, 갱신할 필요가 없다.
3. 정답 코드
import sys
sys.stdin = open("C:/Users/ghtjd/Desktop/tmp/python/input.txt", "r")
# input = sys.stdin.readline
from collections import deque as dq
s = list(input().strip())
l = len(s)
dp_pldm = [[0] * l for j in range(l)] # dp_pldm[i][j] = i인덱스 ~ j인덱스가 팰린드롬 인가?
dp_pldm[0][0] = 1
for i in range(1, l):
dp_pldm[i][i] = 1 # 길이 1 팰린드롬
if s[i] == s[i - 1]:
dp_pldm[i - 1][i] = 1 # 길이 2 팰린드롬
for k in range(3, l + 1): # 길이 3이상 팰린드롬 찾기
for i in range(l - k + 1): # 길이 k, 시작점 i
j = i + k - 1
if s[i] == s[j] and dp_pldm[i + 1][j - 1]:
dp_pldm[i][j] = 1
dp_res = [0] * (l) # 0 ~ i 까지 분할 최소값
for j in range(l): # 끝점 j
for i in range(j + 1): # 시작점 i
if dp_pldm[i][j]:
if dp_res[j] and dp_res[j] <= dp_res[i - 1]:continue
dp_res[j] = dp_res[i - 1] + 1
print(dp_res[l - 1])
반응형
'백준 문제풀이 코드저장소 > Gold' 카테고리의 다른 글
Baekjoon 9527. 1의 개수 세기 (0) | 2024.12.27 |
---|---|
Baekjoon 1766. 문제집 / Python (0) | 2024.12.26 |
Baekjoon 16946. 벽 부수고 이동하기 4 / Python (0) | 2024.12.24 |
Baekjoon 2143. 두 배열의 합 / Python (0) | 2024.12.23 |