确定递推方程:
假如S1的最后一个元素与S2的最后一个元素相等,那么S1和S2的LCS就等于 {S1减去最后一个元素} 与 {S2减去最后一个元素} 的 LCS 再加1。
假如S1的最后一个元素与S2的最后一个元素不等,那么S1和S2的LCS就等于 : {S1减去最后一个元素} 与 S2 的LCS, {S2减去最后一个元素} 与 S1 的LCS 中的较大值。
def lcs(a, b, i, j):
if i < 0 or j < 0:
return 0
if a[i] == b[j]:
return lcs(a, b, i-1, j-1) + 1
else:
l1 = lcs(a, b, i-1, j)
l2 = lcs(a, b, i, j-1)
return max(l1, l2)
注意:i=0、j=0时作为递归结束条件,i、j代表下标,下标为0则表示字符串内的第一个字符。这时仍然可能存在子序列,因此递归结束条件为i<0、j<0。
这里采用分治法(递归)违背了一个原则:
即子问题不重复:
举一个简单例子,在计算lcs(3,4)与 lcs(4,3)时,其递推的下一步可能都为lcs(3,3)。子问题重复,降低运算效率。因此,解决这类问题使用动态规划更为合适。