PAT甲级1045 Favorite Color Stripe (30 分):[C++题解]最佳彩色带、DP、公共子序列变形
文章目錄
- 題目分析
- 題目鏈接
題目分析
來源:acwing
分析:這是一個公共子序列的問題。但是有點變式,序列a和序列b不是完全等價的,序列a的每個元素可以對應多個相同元素,而且有些元素可以不使用。比如下例樣例,a ={2 3 1 5 6},b ={2 2 4 1 5 5 6 3 1 1 5 6}
a和b的公共子序列可以是:
a取: 2 1 5 6
b取: 2 2 1 1 1 5 6
a只取了一部分,b也取了一部分,但是我們可以看到:a中的一個數可以對應到b中的幾個數。
按照最長公共子序列的方式來分析
狀態表示:
f[i][j]f[i][j]f[i][j]表示分別在a[1]a[1]a[1]~ a[i]a[i]a[i]和b[1]b[1]b[1] ~b[j]b[j]b[j]中取的最長公共子序列的長度。
狀態計算:
請注意:當a[i]==b[j]a[i] == b[j]a[i]==b[j]時,轉移不是f[i?1][j?1]+1f[i-1][j-1]+1f[i?1][j?1]+1,而是f[i][j?1]+1f[i][j-1]+1f[i][j?1]+1,這是因為序列a中的數a[i]a[i]a[i]可以對應多個b序列中的數!!
請注意:根據f[i][j]f[i][j]f[i][j]的定義,上圖中藍色情況的計算公式f[i?1][j?1]f[i-1][j-1]f[i?1][j?1]可以包含在f[i?1][j]f[i-1][j]f[i?1][j]或f[i][j?1]f[i][j-1]f[i][j?1]里面,所以能用到的公式就是上面三個紅色公式。當然寫上也不錯,只不過有冗余計算。
多出冗余計算的版本
#include<bits/stdc++.h> using namespace std; const int N =210, M =10010;int n ,m , l; int a[N], b[M]; int f[N][M];int main(){cin >> n;cin >> m;for(int i =1; i<= m; i++) cin>> a[i];cin >> l;for(int i = 1;i <= l; i++) cin >> b[i];for(int i=1; i<= m; i++){for(int j = 1; j<= l; j++){f[i][j] = max(f[i-1][j-1],f[i-1][j]);f[i][j] = max(f[i][j],f[i][j-1]);if(a[i] == b[j])f[i][j] = max(f[i][j] , f[i][j-1]+1);}}cout << f[m][l]<<endl; }或者少些冗余計算的ac代碼
#include<bits/stdc++.h> using namespace std; const int N =210, M =10010;int n ,m , l; int a[N], b[M]; int f[N][M];int main(){cin >> n;cin >> m;for(int i =1; i<= m; i++) cin>> a[i];cin >> l;for(int i = 1;i <= l; i++) cin >> b[i];for(int i=1; i<= m; i++){for(int j = 1; j<= l; j++){f[i][j] = max(f[i][j-1],f[i-1][j]);if(a[i] == b[j])f[i][j] = max(f[i][j] , f[i][j-1]+1);}}cout << f[m][l]<<endl; }題目鏈接
PAT甲級1045 Favorite Color Stripe (30 分)
https://www.acwing.com/problem/content/1531/
總結
以上是生活随笔為你收集整理的PAT甲级1045 Favorite Color Stripe (30 分):[C++题解]最佳彩色带、DP、公共子序列变形的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: PAT甲级1007 Maximum Su
- 下一篇: PAT甲级1068 Find More