POJ3280Cheapest Palindrome(区间dp)


Language:
Default

Cheapest Palindrome

Time Limit: 2000MS   Memory Limit: 65536K
Total Submissions: 6227   Accepted: 3032

Description

Keeping track of all the cows can be a tricky task so Farmer John has installed a system to automate it. He has installed on each cow an electronic ID tag that the system will read as the cows pass by a scanner. Each ID tag‘s contents are currently a single
string with length M (1 ≤ M ≤ 2,000) characters drawn from an alphabet of N (1 ≤ N ≤ 26) different symbols (namely, the lower-case roman alphabet).

Cows, being the mischievous creatures they are, sometimes try to spoof the system by walking backwards. While a cow whose ID is "abcba" would read the same no matter which direction the she walks, a cow with the ID "abcb" can potentially register as two
different IDs ("abcb" and "bcba").

FJ would like to change the cows‘s ID tags so they read the same no matter which direction the cow walks by. For example, "abcb" can be changed by adding "a" at the end to form "abcba" so that the ID is palindromic (reads the same forwards and backwards).
Some other ways to change the ID to be palindromic are include adding the three letters "bcb" to the begining to yield the ID "bcbabcb" or removing the letter "a" to yield the ID "bcb". One can add or remove characters at any location in the string yielding
a string longer or shorter than the original string.

Unfortunately as the ID tags are electronic, each character insertion or deletion has a cost (0 ≤ cost ≤ 10,000) which varies depending on exactly which character value to be added or deleted. Given the content of a cow‘s ID tag and the cost of
inserting or deleting each of the alphabet‘s characters, find the minimum cost to change the ID tag so it satisfies FJ‘s requirements. An empty ID tag is considered to satisfy the requirements of reading the same forward and backward. Only letters with associated
costs can be added to a string.

Input

Line 1: Two space-separated integers: N and M

Line 2: This line contains exactly M characters which constitute the initial ID string

Lines 3..N+2: Each line contains three space-separated entities: a character of the input alphabet and two integers which are respectively the cost of adding and deleting that character.

Output

Line 1: A single line with a single integer that is the minimum cost to change the given name tag.

Sample Input

3 4
abcb
a 1000 1100
b 350 700
c 200 800

Sample Output

900

Hint

If we insert an "a" on the end to get "abcba", the cost would be 1000. If we delete the "a" on the beginning to get "bcb", the cost would be 1100. If we insert "bcb" at the begining of the string, the cost would be 350 + 200 + 350 = 900, which is the minimum.

Source

USACO 2007 Open Gold

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
#define N 2005

int dp[N][N],n,m;
int add[N],del[N];
char a[N],ch[N];

int main()
{
	int i,j;
	while(~scanf("%d%d",&n,&m))
	{
		scanf("%s",a);
		int x,y;
		for(i=0;i<n;i++)
		{
			scanf("%s%d%d",ch,&x,&y);
			add[ch[0]-'a']=x;
			del[ch[0]-'a']=y;
		}

		memset(dp,0,sizeof(dp));

		for(i=m-1;i>=0;i--)
		  for(j=i+1;j<m;j++)
			{
			   dp[i][j]=min(dp[i+1][j]+del[a[i]-'a'],dp[i+1][j]+add[a[i]-'a']);
			   int temp=min(dp[i][j-1]+del[a[j]-'a'],dp[i][j-1]+add[a[j]-'a']);
			   dp[i][j]=min(temp,dp[i][j]);
			   if(a[i]==a[j])
					dp[i][j]=min(dp[i][j],dp[i+1][j-1]);
			}

		printf("%d\n",dp[0][m-1]);
	}
	return 0;
}
时间: 2024-08-28 06:59:37

POJ3280Cheapest Palindrome(区间dp)的相关文章

POJ 1159 Palindrome(区间DP/最长公共子序列+滚动数组)

Palindrome Time Limit: 3000MS   Memory Limit: 65536K Total Submissions: 56150   Accepted: 19398 Description A palindrome is a symmetrical string, that is, a string read identically from left to right as well as from right to left. You are to write a

POJ 3280 Cheapest Palindrome ( 区间DP &amp;&amp; 经典模型 )

题意 : 给出一个由 n 中字母组成的长度为 m 的串,给出 n 种字母添加和删除花费的代价,求让给出的串变成回文串的代价. 分析 :  原始模型 ==> 题意和本题差不多,有添和删但是并无代价之分,要求最少操作几次才能是其变成回文串 ① 其实细想之后就会发现如果没有代价之分的话删除和增添其实是一样的,那么除了原串原本拥有的最长回文串不用进行考虑处理,其他都需要进行删除或者增添来使得原串变成回文串,所以只要对原串 S 和其反向串 S' 找出两者的最长公共子串长度 L 再用总长减去 L 即可 ②

POJ 3280:Cheapest Palindrome 区间DP好题

Cheapest Palindrome 题目链接: http://poj.org/problem?id=3280 题意: 给出一个只由小写字母组成的串,可以添加或删除一些字母(添加和删除都需要花费且花费不同),求将这个串改变成一个回文串的最小花费. 题解: 设dp[i][j]是将区间[i,j]改变成回文串的最小花费,则两种情况 ①显而易见,当s[i]==s[j]时,dp[i][j]=dp[i+1][j-1] ②当s[i]!=s[j]时,dp[i][j]有四种可能的取值,区间 [i,j-1] 删除

poj 3280 Cheapest Palindrome(区间DP)

Cheapest Palindrome Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 5995   Accepted: 2922 Description Keeping track of all the cows can be a tricky task so Farmer John has installed a system to automate it. He has installed on each cow a

Uva 10617 Again Palindrome(区间dp)

Again Palindromes Input: Standard Input Output: Standard Output Time Limit: 2 Seconds A palindorme is a sequence of one or more characters that reads the same from the left as it does from the right. For example, Z, TOT and MADAM are palindromes, but

区间DP基础篇之 POJ1159——Palindrome

题目大意:给定一个字符串,求最少插入几个字符让该字符串成为回文串 法一: dp[i][j]表示使区间[i,j]成为回文串最小插入的字符数,则状态转移方程 1.if s[i]==s[len-1] 则:d[i][j]=d[i+1][j-1] 2.else  d[i]=min(dp[i+1][j],dp[i][j-1]) 首尾字符不同的时候,有两种决策. 1.将新字符插在首位,那么状态就变成了dp[i+1][j]了. 2.将新字符插在末尾,则状态就变成了dp[i][j-1]了 .比较两种决策哪种更优就

UVA 10453 Make Palindrome(区间简单DP)

题意:给出一个字符串A,求出需要至少插入多少个字符使得这个字符串变成回文串. 思路:设dp[i][j]为使区间[i, j]变成回文串所需要的最少字符个数. 1.A[i] == A[j的情况]那么dp[i][j] = min(dp[i][j], dp[i + 1][j -1]); 2.或者在第j个位置插入一个字符A[i], dp[i][j] = min(dp[i][j], dp[i][j - 1] + 1); 3.或者在第i个位置插入一个字符A[j], dp[i][j] = min(dp[i][j

LightOJ1044 Palindrome Partitioning(区间DP+线性DP)

问题问的是最少可以把一个字符串分成几段,使每段都是回文串. 一开始想直接区间DP,dp[i][j]表示子串[i,j]的答案,不过字符串长度1000,100W个状态,一个状态从多个状态转移来的,转移的时候要枚举,这样时间复杂度是不可行的. 然后我就想降维度了,只能线性DP,dp[i]表示子串[0,i]的答案.这样可以从i-1转移到i,str[i]单独作一段或者str[i]能和前面的组成回文串,方程如下: dp[i]=min(dp[i-1]+1,dp[j-1]+1) (子串[j,i]是回文串) 现在

HDU 4632 Palindrome subsequence(区间dp,回文串,字符处理)

题目 参考自博客:http://blog.csdn.net/u011498819/article/details/38356675 题意:查找这样的子回文字符串(未必连续,但是有从左向右的顺序)个数. 简单的区间dp,哎,以为很神奇的东西,其实也是dp,只是参数改为区间,没做过此类型的题,想不到用dp,以后就 知道了,若已经知道[0,i],推[0,i+1], 显然还要从i+1 处往回找,dp方程也简单: dp[j][i]=(dp[j+1][i]+dp[j][i-1]+10007-dp[j+1][