最长公共子序列

什么是最长公共子序列呢?好比一个数列 S,如果分别是两个或多个已知数列的子序列,且是所有符合此条件序列中最长的,则S 称为已知序列的最长公共子序列。

举个例子,如:有两条随机序列,如 1 3 4 5 5 ,and 2 4 5 5 7 6,则它们的最长公共子序列便是:4 5 5。

提示:最容易想到的算法是穷举搜索法,但考虑到最长公共子序列问题也有最优子结构性质,可以用动态规划解决。

#define N 100

stack<int> findLCS(int* arr1, int* arr2, int len1, int len2) {
	int dp[N][N] = { 0 };
	stack<int> stk;

	for (int i = 1; i <= len1; ++i) {
		for (int j = 0; j <= len2; ++j) {
			if (arr1[i - 1] == arr2[j - 1]) {
				/*以arr1[i-1]作为末尾元素, 加上[0~(i-2)],[0~(j-2)] 中的LCS*/
				dp[i][j] = dp[i - 1][j - 1] + 1;
			} else {
				/*若为dp[i][j-1]表示求[0~(i-1)],[0~(j-2)] 中的LCS*/
				dp[i][j] = max(dp[i][j - 1], dp[i - 1][j]);
			}
		}
	}

	int i = len1, j = len2;
	while (dp[i][j] && i > 0 && j > 0) {
		if (dp[i - 1][j] == dp[i][j - 1]) {
			stk.push(arr1[i - 1]);
			i--;
			j--;
		} else {
			if (dp[i - 1][j] == dp[i][j]) {
				i--;
			} else if (dp[i][j - 1] == dp[i][j]) {
				j--;
			}
		}
	}
	return stk;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值