问题描述
对于长度相同的两个字符串 A 和 B,其距离定义为相应位置字符距离之和。两个非空格字符的距离是它们的 ASCII 编码之差的绝对值。空格与空格的距离为 0,空格与其他字符的距离为一定值 k。

在一般情况下,字符串 A 和 B 的长度不一定相同。字符串 A 的扩展是在 A 中插入若干空格字符产生的字符串。在字符串 A 和 B 的所有长度相同的扩展中,有一对距离最小的扩展,该距离称为字符串 A 和 B 的扩展距离。

算法设计
对于给定的字符串 A 和 B,试设计一个算法,计算其扩展距离。

数据输入

输入文件 input.txt 给出输入数据。第 1 行是字符串 A,第 2 行是字符串 B,第 3 行是空格与其他字符的距离定值 k。

结果输出
将计算出的字符串 A 和 B 的扩展距离输出到文件 output.txt

input.txt
cmc
snmn
2

output.txt
10

#include 
#include
using namespace std;

/*
cmc
snmn
2
动态规划,拥有最优子结构,设数组dp[i][j]表示str1的前i个字符和str2的前j个字符的距离最小值(i<=m,j<=n) 
dp[i][j]可以由三种情况转换而来 
1、str1的第i个字符前加空格,str2不加空格,则dp[i][j] = dp[i][j-1]+k;加了空格之后,想对于原字符串,str2消耗了一个字符,str1没消耗,因此是从dp[i][j-1]转移过来 
2、str1不加空格,str2的第j个字符前加空格,则dp[i][j] = dp[i-1][j]+k;同上 
3、str1和str2都不加空格,则dp[i][j] = dp[i-1][j-1]+dist(str1[i],str2[j]);两个字符串都会消耗一个字符,因此是从dp[i-1][j-1]转移过来 
4、都加空格没有意义 
*/ 

string str1, str2; int k;//空格与其他字符的距离 
int dis(char c1, char c2){//计算两个字符之间的距离 
    return abs(c1-c2); 
} 
int get_min(int a, int b, int c, int d){//获取四个值中的最小值 
    return min(a,min(b,min(c,d))); 
} 
void solve(){ 
    cin>>str1>>str2>>k;
    int m = str1.length(), n = str2.length();
    int dp[m+1][n+1];//dp[i][j]表示str1的前i个字符和str2的前j个字符的距离最小值

    for(int i=0;i<=m;i++){
        for(int j=0;j<=n;j++){
            //特殊处理两个字符为空的情况
            if(i==0 && j==0) {
                dp[i][j] = 0; 
                continue;
            }
            //特殊处理某一字符为空的情况
            if(i==0||j==0){
                //直接将空字符按空格填满
                dp[i][j] = k*(i+j);
                continue;
            }
            dp[i][j] = 1e9;
            dp[i][j] = get_min(dp[i][j], dp[i-1][j]+k, dp[i][j-1]+k, dp[i-1][j-1]+dis(str1[i-1],str2[j-1]));
        }
    }
    cout<<dp[m][n]<<endl;
}
int main(){
    solve();
    return 0;
}