题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4323
经典的编辑距离DP,进行一些必要的剪枝,也就是初始长度差大于small的话
直接continue;
#include <iostream>
#include <string.h>
#include <algorithm>
#include <stdio.h>
using namespace std;
#define maxn 1500
#define MIN(a,b) (a<b?a:b)
#define inf 1<<30
char str[maxn][20];
int length[maxn],small;
int dp[20][20];
char str1[maxn];
int len1,len2,n,m;
bool is_ok(char *s1,char *s2,int len1,int len2){
int i,j,k;
for(i=0;i<11;i++)
dp[i][0]=dp[0][i]=i;
for(i=1;i<=len1;i++)
for(j=1;j<=len2;j++){
dp[i][j]=inf;
if(s1[i]==s2[j]) dp[i][j]=dp[i-1][j-1];
k=MIN(dp[i-1][j]+1,dp[i][j-1]+1);
dp[i][j]=MIN(dp[i][j],k);
dp[i][j]=MIN(dp[i][j],dp[i-1][j-1]+1);
}
return dp[len1][len2]<=small;
}
int main(){
int i,j,k,t,cas=0,ans;
scanf("%d",&t);
while(t--){
printf("Case #%d:\n",++cas);
scanf("%d%d",&n,&m);
for(i=0;i<n;i++){
str[i][0]='a';
scanf("%s",str[i]+1);
length[i]=strlen(str[i]);
}
for(i=0;i<m;i++){
str1[0]='a';
scanf("%s%d",str1+1,&small);
k=strlen(str1);
ans=0;
for(j=0;j<n;j++){
if(abs(k-length[j])>small) continue;
if(is_ok(str[j],str1,length[j],k)) ans++;
}
printf("%d\n",ans);
}
}
return 0;
}