2012-08-28 65 views
4

Ruby diff-lcs library在生成需要從一個序列到另一個序列的變更集方面做得非常出色,但是輸出的格式對我來說有點令人困惑。我希望有一個更改列表,但輸出始終是包含一個或兩個更改列表的列表。有多個變更清單的含義/意圖是什麼?Ruby「diff-lcs」diff輸出的一般格式是什麼?

考慮以下簡單的例子:

> Diff::LCS.diff('abc', 'a-c') 
# => [[#<Diff::LCS::Change:0x01 @action="-", @position=1, @element="b">, 
#  #<Diff::LCS::Change:0x02 @action="+", @position=1, @element="-">], 
#  [#<Diff::LCS::Change:0x03 @action="-", @position=3, @element="">]] 

忽略的事實是the last change is blank,爲什麼有變化,而不是隻是一個兩個列表?

回答

3

你可能會有更好的運氣,更好的例子。如果你這樣做:

Diff::LCS.diff('ab cd', 'a- c_') 

那麼輸出看起來像這樣(與噪聲去除):

[ 
    [ 
    <@action="-", @position=1, @element="b">, 
    <@action="+", @position=1, @element="-"> 
    ], [ 
    <@action="-", @position=4, @element="d">, 
    <@action="+", @position=4, @element="_"> 
    ] 
] 

如果我們看一下Diff::LCS.diff('ab cd ef', 'a- c_ e+'),那麼我們會得到三個內部陣列,而不是兩個。

這有什麼可能的原因? diff中有三種操作:

  1. 添加一個字符串。
  2. 刪除字符串。
  3. 更改一個字符串。

的變化其實只是消除了組合,並增加了所以我們只剩下刪除添加的基本操作;這些值非常好地與@action值一致。但是,當人們看差異時,我們希望看到一個作爲一個獨特的操作,我們希望看到b已成爲-,「刪除b,添加-」版本是一個實現細節。

如果所有我們是這樣的:

[ 
    <@action="-", @position=1, @element="b">, 
    <@action="+", @position=1, @element="-">, 
    <@action="-", @position=4, @element="d">, 
    <@action="+", @position=4, @element="_"> 
] 

,那麼你就必須找出哪些+/-雙是真正的改變,哪些是獨立的添加和移除。

所以內部數組映射兩種最基本的操作(添加刪除)三個操作(添加刪除變化)人類希望看到的。

您可能要檢查這些輸出,以及結構:

  • Diff::LCS.diff('ab cd', 'a- x c_')
  • Diff::LCS.diff('ab', 'abx')
  • Diff::LCS.diff('ab', 'xbx')

我覺得一個明確的變化@actionDiff::LCS::Change會更好,但至少是內部陣列讓您將單個添加和刪除分組到更高級別編輯

+0

啊是的,這看起來是正確的 - 每個內部數組代表一個「變化」(一個「刪除/添加」對在同一位置)。所以'Diff :: LCS.diff('a1 b2 c3 d4','aw bx cy dz')。size#=> 4'因爲有四個變化。謝謝! – maerics

+0

@maerics:是的,如果只有一個平面編輯列表,您必須手動匹配「@位置」值以從ASM級別列表「Diff :: LCS ::」中提取C級編輯Change's。 [Perl版本的文檔](http://search.cpan.org/dist/Algorithm-Diff/lib/Algorithm/Diff.pm#diff)值得一看:「描述是* hunk的列表* ;每個大塊代表應該添加,刪除或替換的項目的連續部分。'diff'的返回值是一個hunk的列表...' –

+0

我理解數組的數組結構,但我是仍然想知道我將如何獲得人性化的差異。比如'old content'包裹在'del'標籤中,'new sentence'包裹在'add'標籤中。 – Archonic

相關問題