最长公共子序列算法利用的算法
算法,最长公共子序列

最长公共子序列(LCS)问题(非连续子序列)的两种解法最长公共子序列也称作最长公共子串,英文缩写是LCS(Longest Common Subsequence)。
其定义是:一个序列S,如果分别是两个或多个已知序列的子序列,且是符合此条件的子序列中最长的,则称S为已知序列的最长公共子序列。
关于子序列的定义通常有两种方式,一种是对子序列没有连续的要求,其子序列的定义就是原序列中删除若干元素后得到的序列。
另一种是对子序列有连续的要求,其子序列的定义是原序列中连续出现的若干个元素组成的序列。
求解子序列是非连续的最长公共子序列问题是一个十分实用的问题,它可以描述两段文字之间的“相似度”,即它们的雷同程度,从而能够用来辨别抄袭。
本文将介绍对子序列没有连续性要求的情况下如何用计算机解决最长公共子序列问题,对子序列有连续性要求的情况下如何用计算机解决最长公共子序列问题将在后续的文章中介绍。
一、动态规划法(Dynamic Programming)最长公共子序列问题应该是属于多阶段决策问题中求最优解一类的问题,凡此类问题在编制计算机程序时应优先考虑动态规划法,如果不能用动态规划法,而且也找不到其它解决方法,还可以考虑穷举法。
对于这个问题,只要能找到描述最长公共子序列的最优子结构和最优解的堆叠方式,并且保证最优子结构中的每一次最优决策都满足“无后效性”,就可以考虑用动态规划法。
使用动态规划法的关键是对问题进行分解,按照一定的规律分解成子问题(分解后的子问题还可以再分解,这是个递归的过程),通过对子问题的定义找出最优子结构中最优决策序列(对于子问题就是最有决策序列的子序列)以及最优决策序列子序列的递推关系(当然还包括递推关系的边界值)。
如果一个给定序列的子序列是在该序列中删去若干元素后得到的序列,也就意味着子序列在原序列中的位置索引(下标)保持严格递增的顺序。
例如,序列S = <B,C,D,B>是序列K = <A,B,C,B,D,A,B>的一个子序列(非连续),序列S的元素在在K中的位置索引I = [2,3,5,7],I是一个严格递增序列。
最长公共子序列算法

最长公共子序列算法最长公共子序列算法概述最长公共子序列(Longest Common Subsequence,LCS)是一种常见的字符串匹配问题。
给定两个字符串S和T,求它们的最长公共子序列,即在S和T中都出现的最长的子序列。
该问题可以用动态规划算法解决。
算法原理动态规划算法是一种将复杂问题分解成更小的子问题来解决的方法。
在LCS算法中,我们将两个字符串S和T分别看作X和Y,并定义一个二维数组c[i][j]表示X[1..i]和Y[1..j]的LCS长度。
则有以下递推公式:c[i][j] = 0, if i=0 or j=0c[i][j] = c[i-1][j-1]+1, if X[i]=Y[j]c[i][j] = max(c[i-1][j], c[i][j-1]), if X[i]!=Y[j]其中第一行和第一列均初始化为0,因为空字符串与任何字符串的LCS长度均为0。
当X[i]=Y[j]时,说明当前字符相同,那么当前字符可以加入到LCS中,所以LCS长度加1;否则当前字符不能加入到LCS中,则需要从上一个状态继承得到当前状态。
最终结果即为c[m][n],其中m和n分别表示X和Y的长度。
算法实现以下是LCS算法的Python实现:def lcs(X, Y):m = len(X)n = len(Y)c = [[0] * (n+1) for i in range(m+1)]for i in range(1, m+1):for j in range(1, n+1):if X[i-1] == Y[j-1]:c[i][j] = c[i-1][j-1] + 1else:c[i][j] = max(c[i-1][j], c[i][j-1])return c[m][n]其中X和Y分别为两个字符串。
算法优化以上算法的时间复杂度为O(mn),其中m和n分别表示X和Y的长度。
如果X和Y较长,算法会很慢。
但是我们可以通过一些优化来降低时间复杂度。
最长公共子序列

最长公共子序列GE GROUP system office room 【GEIHUA16H-GEIHUA GEIHUA8Q8-动态规划一、问题描述用动态规划法求两个字符串A=‘xzyzzyx’和B=‘zxyyzxz’的最长公共子序列二、算法分析(1)、若xm=yn,则zk=xm=yn,且Zk-1是Xm-1和Yn-1的最长公共自序列;(2)、若xm≠yn,且zk≠xm,则Zk是Xm-1和Yn的最长公共自序列;(3)、若xm≠yn,且zk≠yn,则Zk是Xm和Yn-1的最长公共自序列;设L(m,n)表示序列X={x1,x2,…,xm}和Y={y1,y2,…,yn}的最长公共子序列的长度L表示已经决策的长度S表示每个决策的状态L(0,0)=L(0,j)=0 1≤i≤m, 1≤j≤nL(i-1,j-1)+1 xi=yi,i≥1,j≥1 L(i,j)=max{L(i,j-1),(L(i-1,j)} xi≠yi,i≥1,j≥1 1 xi=yiS(i,j)= 2 xi≠yi 且L(i,j-1)≥L(i-1,j)3 xi≠yi 且L(i,j-1)< L(i-1,j)长度矩阵L三、源代码#include <iostream>#include <string>using namespace std;int main(){string str1 = "xzyzzyx";string str2 = "zxyyzxz";int x_len = str1.length();int y_len = str2.length();int arr[50][50] ={{0,0}};int i = 0;int j = 0;for(i = 1; i <= x_len; i++){for(j = 1; j <= y_len; j++){if(str1[i - 1] == str2[j - 1]){arr[i][j] = arr[i - 1][j - 1] + 1;}else if(arr[i][j - 1] >= arr[i - 1][j]) arr[i][j] = arr[i][j - 1];elsearr[i][j] = arr[i -1][j];}}for(i = 0 ; i <= x_len; i++){for( j = 0; j <= y_len; j++){cout << arr[i][j] << " ";}cout << endl;}for(i = x_len, j = y_len; i >= 1 && j >= 1;) {if(str1[i - 1] == str2[j - 1]){cout << str1[i - 1] << " ";i--;j--;}else if(arr[i][j -1] > arr[i - 1][j]) j--;elsei--;}cout << endl;return 0;}。
北语网院20春《算法与数据分析》作业_1答案

(单选)1:下列随机算法中运行时有时候成功有时候失败的是A:数值概率算法
B:舍伍德算法
C:拉斯维加斯算法
D:蒙特卡罗算法
正确答案:C
(单选)2:最长公共子序列算法利用的算法是
A:分支界限法
B:动态规划法
C:贪心法
D:回溯法
正确答案:B
(单选)3:矩阵连乘问题的算法可由什么设计实现
A:分支界限算法
B:动态规划算法
C:贪心算法
D:回溯算法
正确答案:B
(单选)4:下列哪一种算法不是随机化算法
A:蒙特卡罗算法
B:.拉斯维加斯算法
C:.动态规划算法
D:.舍伍德算法
正确答案:C
(单选)5:贪心算法与动态规划算法的共同点是
A:重叠子问题
B:构造最优解
C:贪心选择性质
D:最优子结构性质
正确答案:D
(单选)6:下面哪种函数是回溯法中为避免无效搜索采取的策略A:递归函数
B:.剪枝函数
C:。
随机数函数
D:.搜索函数
正确答案:B
(单选)7:采用最大效益优先搜索方式的算法是
A:分支界限法。
最长公共子序列问题

最长公共子序列问题
由最长公共子序列的最优子结构性质可知,要找出X=(x1,x2…xm)和Y=(y1,y2…ym)的最长公共子序列,可以按照下列方式递归进行:
当x(m)=y(n)时,找出x(m-1)和y(m-1)的最长公共子
序列,然后在其尾部加上x(m),即可得到X和Y的最长公共子序列。
当x(m)!=y(n)时,必须解两个子问题,即找出X(m-1)和Y的最长公共子序列,找出X与Y(n-1)的最长公共子序列,两者的最大值即为X和Y的最长公共子序列。
当X或者Y其中一个为空集,则最长公共子序列为0.
第一个方法可以求出最长公共子序列的长度,同时记录每种情况,第二个方法根据情况进行递归求出最长公共子序列。
算法设计与分析复习题目及答案 (3)

分治法1、二分搜索算法是利用(分治策略)实现的算法。
9. 实现循环赛日程表利用的算法是(分治策略)27、Strassen矩阵乘法是利用(分治策略)实现的算法。
34.实现合并排序利用的算法是(分治策略)。
实现大整数的乘法是利用的算法(分治策略)。
17.实现棋盘覆盖算法利用的算法是(分治法)。
29、使用分治法求解不需要满足的条件是(子问题必须是一样的)。
不可以使用分治法求解的是(0/1背包问题)。
动态规划下列不是动态规划算法基本步骤的是(构造最优解)下列是动态规划算法基本要素的是(子问题重叠性质)。
下列算法中通常以自底向上的方式求解最优解的是(动态规划法)备忘录方法是那种算法的变形。
(动态规划法)最长公共子序列算法利用的算法是(动态规划法)。
矩阵连乘问题的算法可由(动态规划算法B)设计实现。
实现最大子段和利用的算法是(动态规划法)。
贪心算法能解决的问题:单源最短路径问题,最小花费生成树问题,背包问题,活动安排问题,不能解决的问题:N皇后问题,0/1背包问题是贪心算法的基本要素的是(贪心选择性质和最优子结构性质)。
回溯法回溯法解旅行售货员问题时的解空间树是(排列树)。
剪枝函数是回溯法中为避免无效搜索采取的策略回溯法的效率不依赖于下列哪些因素(确定解空间的时间)分支限界法最大效益优先是(分支界限法)的一搜索方式。
分支限界法解最大团问题时,活结点表的组织形式是(最大堆)。
分支限界法解旅行售货员问题时,活结点表的组织形式是(最小堆)优先队列式分支限界法选取扩展结点的原则是(结点的优先级)在对问题的解空间树进行搜索的方法中,一个活结点最多有一次机会成为活结点的是( 分支限界法).从活结点表中选择下一个扩展结点的不同方式将导致不同的分支限界法,以下除( 栈式分支限界法)之外都是最常见的方式.(1)队列式(FIFO)分支限界法:按照队列先进先出(FIFO)原则选取下一个节点为扩展节点。
(2)优先队列式分支限界法:按照优先队列中规定的优先级选取优先级最高的节点成为当前扩展节点。
最长公共子序列算法分析

求连续的最长公共子串•首先我们来分析一个简单例子。
•LCS(‘212325233’,’312123223’)=‘21232’•我们看是如何求解出来的,如下图,红色下划线表示已匹配。
分析•从前面例子可以看出解题思路:•每次都是将子串的每一位与母串的每一位比较,然后根据比较的结果找LCS。
因此,我们需要借助一个二维数组存储两个串比较后的结果,用1表示匹配成功,0表示不成功。
如匹配结果如下图(1),最长公共子串见图(2)。
进一步分析•在0和1的矩阵中找最长的1对角线序列又要花去一定的时间。
通过改进矩阵的生成方式和设置标记变量,可以省去这部分时间。
下面是新的矩阵生成方式:算法•设置一个矩阵,记录两个串的匹配情况。
•当字符匹配的时候,不是简单的给相应元素赋上1,而是赋上其左上角元素的值加1。
•我们用两个标记变量来标记矩阵中值最大的元素的位置,在矩阵生成的过程中来判断•当前生成的元素的值是不是最大的,据此来改变标记变量的值,那么到矩阵完成的时候,最长匹配子串的位置和长度就已经出来了。
•显然该算法的时间复杂度为两个串的长度乘积。
for(i=1;i<=row;i++) {for(j=1;j<=col;j++) {if(s[i-1]==rs[j-1]) {lcs[i][j]=lcs[i-1][j-1]+1;}else{if(lcs[i-1][j]>=lcs[i][j-1]) {lcs[i][j]=lcs[i-1][j];}else {lcs[i][j] = lcs[i][j-1];}}}}return lcs[row][col];}。
算法分析与设计试题

一、选择题(20分)1.最长公共子序列算法利用的算法是(B )。
A、分支界限法B、动态规划法C、贪心法D、回溯法2.实现棋盘覆盖算法利用的算法是(A )。
A、分治法B、动态规划法C、贪心法D、回溯法3.下面是贪心算法的基本要素的是(C )。
A、重叠子问题B、构造最优解C、贪心选择性质D、定义最优解4.回溯法的效率不依赖于下列哪些因素( D )A.满足显约束的值的个数B. 计算约束函数的时间C. 计算限界函数的时间D. 确定解空间的时间5.下面哪种函数是回溯法中为避免无效搜索采取的策略(B )A.递归函数 B.剪枝函数C。
随机数函数 D.搜索函数6.采用最大效益优先搜索方式的算法是(A )。
A、分支界限法B、动态规划法C、贪心法D、回溯法7.贪心算法与动态规划算法的主要区别是(B )。
A、最优子结构B、贪心选择性质C、构造最优解D、定义最优解8. 实现最大子段和利用的算法是(B )。
A、分治策略B、动态规划法C、贪心法D、回溯法9.优先队列式分支限界法选取扩展结点的原则是(C )。
A、先进先出B、后进先出C、结点的优先级D、随机10.下列算法中通常以广度优先方式系统搜索问题解的是(A)。
A、分支限界法B、动态规划法C、贪心法D、回溯法二、填空题(22分每空2分)1.算法是由若干条指令组成的有穷序列,且要满足输入、输出、确定性和有限性四条性质。
2、大整数乘积算法是用分治法来设计的。
3、以广度优先或以最小耗费方式搜索问题解的算法称为分支限界法。
4、舍伍德算法总能求得问题的一个解。
5、贪心选择性质是贪心算法可行的第一个基本要素,也是贪心算法与动态规划算法的主要区别。
6.快速排序template<class Type>void QuickSort (Type a[], int p, int r){if (p<r) {int q=Partition(a,p,r);QuickSort (a,p,q-1); 哈密顿环问题的算法可由回溯法设计实现。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
最长公共子序列算法利用的算法
最长公共子序列(LCS)算法利用了递归算法和动态规划算法。
递归算法的代码如下:
```c
#include<stdio.h>
#include<string.h>
char a[30], b[30];
int m, n;
int lcs(int i, int j) {
if (i >= m || j >= n) //限定跳出条件
return 0;
if (a[i] == b[j]) //相等时都往后移动一位
return lcs(i+1, j+1) + 1;
else //比较得到较大的那一个
return lcs(i +1, j) > lcs(i, j + 1)? lcs(i + 1, j) : lcs(i, j + 1);
}
int main() {
strcpy(a, "CNBLOG");
strcpy(b, "BELONG");//利用strcpy函数存储字符串
m = strlen(a);
n = strlen(b);
printf("%d\n", lcs(0,0));
return 0;
}
```
递归算法的思路是利用一层层往上找,用栈存储,但随着数据规模的增加,算法的复杂度会以指数级增长,因此一般不采用递归算法。
动态规划算法采用二维数组来标识中间计算结果,避免重复的计算来提高效率。
设有字
符串a(0…n),b(0…m),递推公式如下:
字符串a对应的是二维数组num的行,字符串b对应的是二维数组num的列。
另外,采用二维数组flag来记录下标i和j的走向。
数字”1”表示斜向下,数字”2”表示水平向右,数字”3”表示竖直向下。
这样便于以后的求解最长公共子序列。