刷题——Cheapest Palindrome POJ - 3280

/*
给定一个串和改变串的代价(串可变长变短),问令给定串变成回文串的最小代价
增加一个字符和减少一个字符各有代价,这时选取最少最小的作为改变这个字符的代价(删掉和增加都满足变化)
dp[i][j]表示以i为头j为尾的串,i<j,ij间的距离从1开始增加,不断使得dp[i][j]中距离比i,j小的串是回文串
dp[i][j]:
a[i]==a[j],dp[i][j]=dp[i+1][j-1]
a[i]!=a[j],dp[i][j]=min(dp[i][j],dp[i][j-1]+ad[a[j]-'a'],dp[i+1][j]+ad[a[i]-'a'])
*/
#include <stdio.h>
#include <algorithm>
#include <string.h>
using namespace std;
#define INF 1e8
int n,m;
char a[2005];
int ad[30];
int dp[2005][2005];
int main(){
    while(~scanf("%d %d",&n,&m)){
        scanf("%s",a);
        memset(dp,0,sizeof(dp));
        memset(ad,0,sizeof(ad));
        for(int i=0;i<n;i++){
            char c[2];
            int s,t;
            scanf("%s",c);
            scanf("%d %d",&s,&t);
            ad[c[0]-'a']=min(s,t);
        }
        for(int k=1;k<m;k++){
            for(int i=0,j=k;j<m;i++,j++){
                dp[i][j]=INF;
                if(a[i]==a[j]){
                    dp[i][j]=dp[i+1][j-1];
                }
                else{
                    dp[i][j]=min(dp[i][j],dp[i][j-1]+ad[a[j]-'a']);
                    dp[i][j]=min(dp[i][j],dp[i+1][j]+ad[a[i]-'a']);
                }
            }
        }
        printf("%d\n",dp[0][m-1]);
    }
    return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章