Dynamic Programming of LCS

table of Contents

Longest common subsequence (Longest Common Subsequence) does not require continuous

Longest common substring (Longest Common Substring) require continuous

Three longest common subsequence string


Longest common subsequence (Longest Common Subsequence) does not require continuous

 https://leetcode-cn.com/problems/delete-operation-for-two-strings/

class Solution {
public:
    int minDistance(string word1, string word2) {
        int lena=word1.length();
        int lenb=word2.length();
        int a[lena+1][lenb+1] = {0};
        int len = 0;          
        for(int i=0;i<=lena;i++)
            for(int j=0;j<=lenb;j++){
                if(i==0||j==0)
                    a[i][j]=0;
                else if(word1[i-1]==word2[j-1]){
                    a[i][j]=a[i-1][j-1]+1;
                }
                else a[i][j]=max(a[i-1][j],a[i][j-1]);
            }
        return a[lena][lenb];        
    }
};

Longest common substring (Longest Common Substring) require continuous

https://leetcode-cn.com/problems/maximum-length-of-repeated-subarray/ 

class Solution {
public:
    int findLength(vector<int>& A, vector<int>& B) {
        int lena=A.size();
        int lenb=B.size();
        int a[lena+1][lenb+1] = {0};
        int len = 0;          
        for(int i=0;i<=lena;i++)
            for(int j=0;j<=lenb;j++){
                if(i==0||j==0)
                    a[i][j]=0;
                else if(A[i-1]==A[j-1]){
                    a[i][j]=a[i-1][j-1]+1;
                    len=max(len,a[i][j]);
                }
                else a[i][j]=0;
            }
        return len;        
    }
};

Three longest common subsequence string

Myth: First find the longest common subsequence first two strings, and then ask him the longest common subsequence and third string.

As a simple example, three strings are abc, cab, c, the first two of the longest common subsequence common subsequence is ab, ab and c is empty, they actually have a character c, so this approach is wrong.

#include <iostream>
#include <string>
#include <algorithm>
 
using namespace std;
const int MAXN = 101;	//字符串的最大长度位MAXN-1
int a[MAXN][MAXN][MAXN];//a[i][j][k]表示第一个字符串的前i个字符,第二个字符串的前j个字符和
						//第三个字符串的前k个字符的最长公共子序列的长度
//函数返回三个字符串的最长公共子序列的长度
int commonLen(string strA, string strB, string strC)
{
	//n1、n2、n3分别为三个字符串的长度
	int n1 = strA.size();
	int n2 = strB.size();
	int n3 = strC.size();
 
	//字符串的个数可以是0-n,共n+1个可能,所以循环中是i<=n
	for(int i = 0; i <= n1; i++)
	for(int j = 0; j <= n2; j++)
	for(int k = 0; k <= n3; k++)
		if(i == 0 || j == 0 || k == 0)	//只要有一个序列的长度为0,公共子序列的长度为0
			a[i][j][k] = 0;
	//自底向上求a[i][j][k]
	for(int i = 1; i <= n1; i++)
		for(int j = 1; j <= n2; j++)
			for(int k = 1; k <= n3; k++)
			{
				if(strA[i - 1] == strB[j - 1] && strB[j - 1] == strC[k - 1])
					a[i][j][k] = a[i - 1][j - 1][k - 1] + 1;
				else 
					a[i][j][k] = max(max(a[i - 1][j][k], a[i][j - 1][k]),
									a[i][j][k -1]);
			}
	return a[n1][n2][n3];
}
 
int main()
{
	string str1, str2, str3;
	while(cin >> str1 >> str2 >> str3)
		cout << commonLen(str1, str2, str3) << endl;
 
	return 0;
}

 

Guess you like

Origin blog.csdn.net/a1058420631/article/details/88962669