1 前言
这个4个算法比较相似,并且有以下相同点和不同点
2 异同点
以str1 = "ABCDEF" , str2="ZABCDZE" 为例
相同点:
1、都是在字符串上得到某个目标;2、算法的核心都是动态规划的思想。
不同点:
1、目标不同,其中最大公共字符串是最大连续的子序列,例如:最大公共字符串是"ABCD" ,长度为4。而最大公共子序列是"ABCDE",长度为5。
2、编辑距离,是求从一个字符串str1到另一个字符串str2的变动的最小次数,其中变动只在一个字符串上发生,变动包括三个动作:删除,插入,更改。
3、Myers可能听得比较少,但是作为程序员应该都用过,因为SVN和GIT的版本比对算法,diff是用的这个算法,他可以比较全面的寻找到每一个节点的异同。虽然是动态规划,但是它跟前面的三个算法的遍历方式不同,这也是本质的不同,这里提一下,后面详述。补充一句,对于
不废话了,下面来直接看这三个的实现过程。
3 最大公共字符串(LCS)
最大公共字符串是最大的连续的公共的字符串的长度,既然是动态规划,必然是要有递推式。先写出来。
以str1 = "ABCDEF" , str2="ZABCDZE" 为例, 为 和 的最大公共字符串。则递推如下:
下面开始写代码
def longer_common_string(str1, str2):
"""
最大公共字符串 实现
"""
len1 = len(str1)
len2 = len(str2)
max_lcs_len = 0
max_len_axis = (0, 0)
lcs_matrix = [[0 for j in range(len2+1)] for i in range(len1+1)]
for i, char_1 in enumerate(str1):
for j, char_2 in enumerate(str2):
if char_1 == char_2:
lcs_matrix[i+1][j+1] = lcs_matrix[i][j] + 1
if lcs_matrix[i+1][j+1] > max_lcs_len:
max_lcs_len = lcs_matrix[i+1][j+1]
max_len_axis = (i, j)
else:
lcs_matrix[i+1][j+1] = 0
return max_lcs_len, max_len_axis
str1 = "ABCDEF"
str2 = "ZABCDZE"
lcs_len, axis = longer_common_string(str1, str2)
print(lcs_len)
print(axis)
# print result
# 4
# (3, 4)
得到结果 lcs_len = 4, axis =(3,4),表示最大公共子序列在str1 索引为3的位置结束,在str2索引为4的地方结束。
4 最大公共子序列(LCQ)
子序列可以是非连续的字符串,因此 lcq >= lcs 恒成立。对于递推关系,则要所有改变了&#x