1. 程式人生 > >uva 10453 【回文串區間dp】

uva 10453 【回文串區間dp】

targe 結果 插入 end gpo cout min 輸出 表示

Uva 10453

題意:給定字符串,問最少插入多少個字符使其變成回文串,並任意輸出一種結果。

題解:和Uva 10739類似,這裏是只能增加。類似定義dp[i][j]表示子串Si...Sj變為回文串需要插入字符的最小數。當s[i]==s[j]時,dp[i][j]=dp[i+1][j-1];當兩者不相等時,dp[i][j]=min(dp[i+1][j],dp[i][j-1])+1。然後dp出結果,dfs()輸出答案。

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<cstring>
 4 #include<algorithm>
 5
using namespace std; 6 7 int dp[1050][1050]; 8 char s[1050]; 9 10 void dfs(int l,int r) 11 { 12 if(l>r) return; 13 if(l==r) cout<<s[l]; 14 else if(s[l]==s[r]){ 15 cout<<s[l];dfs(l+1,r-1);cout<<s[r]; 16 }else if(dp[l][r]==dp[l+1][r]+1){ 17 cout<<s[l];dfs(l+1
,r);cout<<s[l]; 18 }else{ 19 cout<<s[r];dfs(l,r-1);cout<<s[r]; 20 } 21 } 22 23 int main() 24 { 25 while(cin>>s) 26 { 27 int len=strlen(s); 28 for(int i=0;i<len;i++) dp[i][i]=0; 29 for(int i=len-1;i>=0;i--) 30 { 31 for
(int j=i+1;j<len;j++){ 32 if(s[i]==s[j]) 33 dp[i][j]=dp[i+1][j-1]; 34 else 35 dp[i][j]=min(dp[i+1][j],dp[i][j-1])+1; 36 } 37 } 38 cout<<dp[0][len-1]<<" "; 39 dfs(0,len-1); 40 cout<<endl; 41 } 42 return 0; 43 }

uva 10453 【回文串區間dp】