苦恼的月下老人(最长子序列)by C++

苦恼的月下老人(最长子序列)by C++

题目要求(题目来源:xmu oj)

描述
传说中,月老是掌管男女婚姻之神。每年七夕,七星娘娘会把人世间未婚的成年男女制成名册,向天庭呈报。月下老人收到名册后,按照个性、善恶、兴趣与条件抄写成一本配偶名册,然后用红线绑牢男女二人之足,使合适的男女配成一对佳偶。在一个古老的小镇,有一条古老的小河横穿这个镇南北,把这个小镇划分成东西两个部分。这个古老的小镇保留着一个古老的风俗,所有未婚男子都住在这条河的西岸上面,所有的未婚女子都住在这条河的东岸。今年月下老人收到了这个小镇上所有未婚男女的名册,他把每个人的个性、善恶、兴趣与条件做了一个简单的汇总,给每个人添加了一个如A B C之类的标签,只有相同标签的男女才有可能用红线绑在一起。原本这个是个很简单的事情,但是现在问题是月老使用的红线,是不能互相交叉的,否则后果会很严重。所以月老为了更多人的幸福,他只能牺牲部分人的幸福。现在月老在纸上笔划了很久,还是没能比划出一个最好的方案,使得让最多对情侣终成眷属。您能帮帮他么?
输入
输入的文件的第一行包含两个整数N,M(0 < N, M <= 1000),分别表示未婚男子和未婚女子的数目。第二行包含一个长度为N的字符串,字符串为大写字母A-Z和小写字母a-z组成,从北到南顺序表示每个男子的标签。第三行包含一个长度为M的字符串,从北到南顺序顺序表示每个女子的标签。
输出
输出一个整数表示月老最多可以为多少对情侣成功牵线。

题目分析

题目内说到 “但是现在问题是月老使用的红线,是不能互相交叉的,否则后果会很严重。” 的意思即为匹配必须顺序进行,两边最后匹配结束后的排列顺序不变。所以这道题就变成了一个寻找最大子序列的匹配问题。这个代码算法书上有记录,直接修改一下书上算法即可。

#include<stdio.h>
#include<string.h>
#include <iostream>

using namespace std;

char a[1005],b[1005];

int num[1005][1005];

void LCS(int lena,int lenb){
    for(int i=1;i<=lena;i++){
        for(int j=1;j<=lenb;j++){
            if(a[i]==b[j]){
                num[i][j]=num[i-1][j-1]+1;
            }
            else{
                num[i][j]=num[i][j-1] >= num[i-1][j] ? num[i][j-1] : num[i-1][j];
            }
        }
    }
}
int main(){
    int lena;
    int lenb;
    cin>>lena>>lenb;
    for(int i = 1 ; i <=lena ; i ++ ){
        cin>>a[i];
    }
    for(int i = 1 ; i <=lenb ; i ++ ){
        cin>>b[i];
    }
    memset(num,0,sizeof(num));//Êý×鸳³õÖµ
    LCS(lena,lenb);
    /*for(int i=0;i<=lena;i++){
        for(int j=0;j<=lenb;j++){
           cout<<num[i][j]<<" ";
        }
        cout<<"\n";
    }*/
    printf("%d",num[lena][lenb]);
    return 0;
}
代码截图:

在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值