#문제
9251번: LCS
https://www.acmicpc.net/problem/9251
9251번: LCS
LCS(Longest Common Subsequence, 최장 공통 부분 수열)문제는 두 수열이 주어졌을 때, 모두의 부분 수열이 되는 수열 중 가장 긴 것을 찾는 문제이다. 예를 들어, ACAYKP와 CAPCAK의 LCS는 ACAK가 된다.
www.acmicpc.net
#접근방법
이전 배열의 값을 이용하는 동적계획법으로 접근하면 된다.
반응형
#풀이
#include <stdio.h>
#include <iostream>
#include <string>
#include <algorithm>
using namespace std;
int arr[1005][1005];
int main(){
string a,b;
int ans = 0;
cin >> a >> b;
for(int i=1;i<=a.size();i++)
for(int j=1;j<=b.size();j++)
if(a[i-1]==b[j-1])
arr[i][j] = arr[i-1][j-1] + 1;
else
arr[i][j] = max(arr[i-1][j],arr[i][j-1]);
printf("%d",arr[a.size()][b.size()]);
return 0;
}
LCS의 로직은 아래와 같다.
- 문자열a,b의 한 글자씩 비교한다.
- 두 문자가 다르다면 arr[i-1][j]와 arr[i][j-1]중에 큰 값을 표시한다.
- 두 문자가 같다면 arr[i-1][j-1]값에 +1을 한다.
- 위 과정을 반복한다.
부분수열은 연속된 값이 아니다. 따라서 현재의 문자를 비교하는 과정 이전의 최대 공통 부분수열은 계속해서 유지가 된다. 현재의 문자를 비교하는 과정 이전의 과정이 바로 arr[i-1][j]와 arr[i][j-1]가 된다.
두 문자가 같으면 지금까지의 최대 공통 부분수열에 1을 더해주면 되므로 arr[i-1][j-1]에 1을 더해준다.
마지막 배열 arr[a.size()][b.size()]을 출력하면 정답이다.
#성능
#정리
LCS의 알고리즘 로직을 알고 있고 이를 구현할 수 있으면 풀 수 있는 문제였다.
'하루 한 문제' 카테고리의 다른 글
[백준] 12851번 : 숨바꼭질 2 [C/C++] (0) | 2021.12.26 |
---|---|
[백준] 9663번 : N-Queen [C/C++] (0) | 2021.12.26 |
[백준] 1916번 : 최소비용 구하기 [C/C++] (0) | 2021.12.23 |
[백준] 1753번 : 최단경로 [C/C++] (2) | 2021.12.22 |
[백준] 16953번 : A → B [C/C++] (0) | 2021.12.21 |