其实这个就是经典的DP,编辑距离,状态转移啥的,在书上讲的很详细,这个题,要输出路径。中间注意在删除和插入的时候要把路径上的位置改变,WA了3次。。。基本上是自己盲查数据查到的。。。开始的时候并不是用队列存的每一种操作,想当然的以为每个位置都只有一个操作,没想清楚,va aaaav。。然后就是这个位置的变化。。。没有注意到插入,注意了插入,又忘记了删除,abcde,deabc。。。总之,过程很曲折。。
1 #include <stdio.h> 2 #include <string.h> 3 char str1[100],str2[100]; 4 int p[101][101],o1[1000],o2[1000]; 5 char str[1000]; 6 int main() 7 { 8 int i,j,k,len1,len2,n,a; 9 while(scanf("%s%s",str1,str2)!=EOF) 10 { 11 memset(p,0,sizeof(p)); 12 memset(o1,0,sizeof(o1));//记录位置 13 memset(o2,0,sizeof(o2));//记录操作 14 memset(str,0,sizeof(str));//记录字符 15 len1 = strlen(str1); 16 len2 = strlen(str2); 17 for(i = 1;i <= len1;i ++) 18 p[i][0] = i; 19 for(i = 1;i <= len2;i ++) 20 p[0][i] = i; 21 for(i = 1;i <= len1;i ++) 22 for(j = 1;j <= len2;j ++) 23 { 24 if(str1[i-1] == str2[j-1]) 25 n = 0; 26 else 27 n = 1; 28 p[i][j] = p[i-1][j-1]+n; 29 if(p[i][j] > p[i-1][j]+1) 30 p[i][j] = p[i-1][j]+1; 31 if(p[i][j] > p[i][j-1]+1) 32 p[i][j] = p[i][j-1]+1; 33 } 34 printf("%d\n",p[len1][len2]); 35 k = 1; 36 for(i = len1,j = len2;;)//寻找路径 37 { 38 n = 0; 39 if(str1[i-1] == str2[j-1]&&i >= 1&&j >= 1) 40 n = 0; 41 else 42 n = 1; 43 if(p[i][j] == p[i-1][j-1]+n&&i >= 1&&j >=1) 44 { 45 if(n == 1) 46 { 47 o1[k] = 1; 48 o2[k] = i; 49 str[k] = str2[j-1]; 50 k ++; 51 } 52 i -- ;j --; 53 } 54 else if(p[i][j] == p[i-1][j]+1&&i >= 1) 55 { 56 o1[k] = 2; 57 o2[k] = i; 58 k ++; 59 i --; 60 } 61 else if(p[i][j] == p[i][j-1]+1&& j >= 1) 62 { 63 o1[k] = 3; 64 o2[k] = i+1; 65 str[k] = str2[j-1]; 66 k ++; 67 j --; 68 } 69 if(i == 0&&j == 0) 70 break; 71 } 72 j = 1; 73 for(i = k-1;i >= 1;i --) 74 { 75 if(o1[i] == 1) 76 printf("%d Replace %d,%c\n",j++,o2[i],str[i]); 77 else if(o1[i] == 2) 78 { 79 printf("%d Delete %d\n",j++,o2[i]); 80 for(a = i-1;a >= 1;a --)//位置变化 81 { 82 if(o2[a] >= o2[i]) 83 o2[a] --; 84 } 85 } 86 else if(o1[i] == 3) 87 { 88 printf("%d Insert %d,%c\n",j++,o2[i],str[i]); 89 for(a = i-1;a >= 1;a --)//位置变化 90 { 91 if(o2[a] >= o2[i]) 92 o2[a] ++; 93 } 94 } 95 } 96 } 97 return 0; 98 }