【问题标题】:Eugene Myers' Diff Algorithm: Finding the Longest Common Subsequence of "A" and "B"Eugene Myers 的 Diff 算法:寻找“A”和“B”的最长公共子序列
【发布时间】:2015-04-14 20:45:53
【问题描述】:

我一直在查看Eugene Myers' Diff Algorithm Paper。这是在流行的diff 程序中实现的算法。

在论文的第 12 页,它给出了算法的伪代码,用于查找 AB 的最长公共子序列:

LCS(A, N, B, M)
    If N > 0 and M > 0 Then
        Find the middle snake and the length of an optimal path for A and B.
        Suppose it is from (x, y) to (u, v).
        If D > 1 Then
            LCS(A[1..x], x, B[1..y], y)
            Output A[x+1..u]
            LCS(A[u+1..N], N-u, B[v+1..M], M-v)
        Else If M > N Then
            Output A[1..N].
        Else
            Output B[1..M].

假设 A = "A" 且 B = "B"。在这种情况下,N = 1 和 M = 1。中间的蛇将是 (x, y) = (0, 1) 和 (u, v) = (0, 1),因为没有对角线。在这种情况下,D = 1,因为算法只采取了一步。

算法说在这种情况下唯一要做的就是Output B[1..M],等于“B”,因为N > 0,M > 0,D = 1,并且M = N。但这似乎是错误的,因为“A”和“B”之间没有共同的子序列。该论文的评论“如果D

我在这里误解了什么?

【问题讨论】:

    标签: algorithm diff


    【解决方案1】:

    你误解了D-path和snake的定义。

    从第 4 页开始:

    令 D 路径为从 (0,0) 开始且具有 D 非对角线的路径 边缘。 0 路径必须仅由对角边组成。通过简单的归纳,可以得出一条 D 路径必须由 (D − 1) 路径后跟一条非对角边,然后是一个可能为空的对角边序列,称为蛇

    因此,在 A = "A" 和 B = "B" 的示例中,最佳路径是 2 路径(一条水平路径和一条垂直路径),中间的蛇是空字符串。我们通过检查知道 LCS 是一个空字符串,但我们想展示用于证明它的算法。

    首先我们需要找到中间的蛇。如果您按照第 11 页的算法找到中间的蛇,您会看到最短编辑脚本的长度为 2 并且 (x,y) = (u,v) = (1,0) 或 (0,1 )。也就是说,它是一条路中间的空蛇。

    算法伪代码有一些不明显的符号约定:

    1. 如果 n ,则 A[m..n] 为空字符串
    2. 在对 LCS 的递归调用中,第一次调用使用上限 (D/2) 作为 D,第二次调用使用下限(D/2)。这在第 12 页算法上方的文字中更清楚地说明了这一点。

    因此,在本例中,假设第一次调用 LCS 找到了一条 (x,y) = (u,v) = (1,0) 的中间蛇,那么由于 D=2,结果是展开的:

    LCS(A[1..1], 1, B[1..0], 0)  // Output nothing since M = 0
    Output A[2..1]               // Output nothing since it is an empty string.
    LCS(A[2..1], 0, B[1..1], 1)  // Output nothing since N = 0
    

    这是正确的,因为这些字符串没有共同的子序列。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-06-14
      • 2012-12-11
      • 1970-01-01
      • 1970-01-01
      • 2011-04-09
      • 2015-12-10
      • 1970-01-01
      • 2011-03-01
      相关资源
      最近更新 更多