题解 P2453 【[SDOI2006]最短距离】

变量c_xxx意为cost_xxx
之后的dp方程就很清晰了,萌新似乎也能看懂(初学OI系列)
kill放到最后统一处理,把各种情况kill到零,比较输出最大值即可
注意!dp[lena][lenb]必须在外面处理,因为ta不用kill,所以不用-1
(我一开始就被坑了,我还是太菜)


#include<bits/stdc++.h>
using namespace std;
int dp[210][210],lena,lenb,ans;//dp[i][j]表示a删i个,b到j个的最小值 
int c_delete,c_replace,c_copy,c_insert,c_twiddle;
char a[210],b[210];
int main()
{
	cin>>a>>b;
	lena=strlen(a);
	lenb=strlen(b);
	cin>>c_delete>>c_replace>>c_copy>>c_insert>>c_twiddle;
	for(int i=1;i<=max(lena,lenb);i++)
	{
		dp[0][i]=c_insert*i;
		dp[i][0]=c_delete*i;
	}
	for(int i=1;i<=lena;i++)
	{
		for(int j=1;j<=lenb;j++)
		{
			dp[i][j]=999999999;//初始化
		}
	}
	for(int i=1;i<=lena;i++)
	{
		for(int j=1;j<=lenb;j++)
		{
			dp[i][j]=min(dp[i][j],dp[i-1][j]+c_delete);
			dp[i][j]=min(dp[i][j],dp[i-1][j-1]+c_replace);
			if(a[i-1]==b[j-1])//我是从0读入的,所以减1
			{
				dp[i][j]=min(dp[i][j],dp[i-1][j-1]+c_copy);
			}
			dp[i][j]=min(dp[i][j],dp[i][j-1]+c_insert);
			if(i>=2&&j>=2&&a[i-1]==b[j-2]&&a[i-2]==b[j-1])//不判前两个会炸
			{
				dp[i][j]=min(dp[i][j],dp[i-2][j-2]+c_twiddle);
			}
		}
	}
	ans=dp[lena][lenb];
	for(int i=0;i<lena;i++)
	{
		ans=min(ans,dp[i][lenb]+(lena-i)*c_delete-1);
	}
	cout<<ans;
}
posted @ 2019-01-28 11:41  G_A_TS  阅读(453)  评论(0编辑  收藏  举报