九度OJ 1042

来源:互联网 发布:淘宝直通车产品在哪里 编辑:程序博客网 时间:2024/05/18 03:32
题目描述:

Find a longest common subsequence of two strings.

输入:

First and second line of each input case contain two strings of lowercase character a…z. There are no spaces before, inside or after the strings. Lengths of strings do not exceed 100.

输出:

For each case, output k – the length of a longest common subsequence in one line.

样例输入:
abcdcxbydz
样例输出:
2

刚开始读题觉得很容易理解,应该是求两个序列的最长公共子序列,印象中也算是比较经典的动态规划题了。
一开始我是这样理解最长公共子序列的:两个序列中连续的相同的子序列。比如,abcgd和arthgbcd中bc是的,没想到这题里面不相邻的acd也算的。怪不得刚开始以为样例里面结果给错了。参照了算法导论才发现这里最长公共子序列的真正含义。
理解了定义之后,便开始解题了。方法是动态规划。
将两个序列<x1,x2,x3,x4,x5……>和序列<Y1,Y2,Y3,Y4,Y5……>的长度记为len1,len2,那么最长公共子序列可以表示为c[len1][len2]
一般的,
1.c[i][j] = 0 (i = 0或者 j = 0)这里的意思是序列里有一个序列是空的,当然最大子序列是空
2.c[i][j] = c[i-1][j-1]  (str1[i] = str2[j])  意思是末尾的两个数相同,递归定义
3.c[i][j] = max(c[i-1][j], c[i][j-1])  (str1[i] != str2[j])


#include <iostream>#include <cstring>using namespace std;int main(){    int c[110][110];    string str1,str2;    while(cin>>str1>>str2){        memset(c,0,sizeof(c));        for(int i=0;i<=str1.length();i++)            c[i][0] = 0;        for(int j=0;j<=str2.length();j++)            c[0][j] = 0;        for(int i=1;i<=str1.length();i++){            for(int j=1;j<=str2.length();j++){                if(str1[i-1] == str2[j-1]){                    c[i][j] = c[i-1][j-1] + 1;                }                else{                    if(c[i-1][j] > c[i][j-1])                        c[i][j] = c[i-1][j];                    else                        c[i][j] = c[i][j-1];                }            }        }        cout<<c[str1.length()][str2.length()]<<endl;    }    return 0;}



0 0
原创粉丝点击