mirror of
https://github.com/flynx/diff.js.git
synced 2025-10-28 10:30:09 +00:00
refactored the LCS + made it more sutible for diffing...
Signed-off-by: Alex A. Naanou <alex.nanou@gmail.com>
This commit is contained in:
parent
9c89adeea7
commit
e7f8029948
130
diff.js
130
diff.js
@ -100,74 +100,81 @@ var _diff_item_order = function(diff, A, B, options, filter){
|
||||
}
|
||||
|
||||
|
||||
// get common chuncs...
|
||||
// XXX add chunk offsets to results...
|
||||
var getCommonSections =
|
||||
function(A, B, a, b, min_chunk, cmp, index){
|
||||
a = a || 0
|
||||
b = b || 0
|
||||
min_chunk = min_chunk || 2
|
||||
// get common chuncs (LCS)...
|
||||
var getCommonSections = function(A, B, cmp, min_chunk){
|
||||
cmp = cmp || function(a, b){
|
||||
return a === b || a == b }
|
||||
index = index || []
|
||||
return a === b || a == b ? a : false }
|
||||
|
||||
var index = index || []
|
||||
// XXX do we actually need this???
|
||||
min_chunk = min_chunk || 1
|
||||
|
||||
var _getCommonSections = function(a, b){
|
||||
// index...
|
||||
var res = (index[a] || [])[b]
|
||||
if(res != null){
|
||||
return res
|
||||
}
|
||||
|
||||
// collect common chunk...
|
||||
var l = 0
|
||||
var chunk = {
|
||||
A: a,
|
||||
B: b,
|
||||
chunk: [],
|
||||
}
|
||||
while(a+l < A.length && b+l < B.length){
|
||||
var e = cmp(A[a+l], B[b+l])
|
||||
if(!e){
|
||||
break
|
||||
}
|
||||
chunk.chunk.push(e)
|
||||
l++
|
||||
}
|
||||
// discard small chunks...
|
||||
l = l < min_chunk ? 0 : l
|
||||
|
||||
// get next chunks...
|
||||
var L = A.length > a+l + min_chunk ?
|
||||
_getCommonSections(l+a+1, l+b)
|
||||
: [0]
|
||||
var R = B.length > b+l + min_chunk ?
|
||||
_getCommonSections(l+a, l+b+1)
|
||||
: [0]
|
||||
|
||||
// select the best chunk-set...
|
||||
// NOTE: we maximize the number of elements in a chunk set then
|
||||
// minimize the number of chunks per set...
|
||||
var next = L[0] == R[0] ?
|
||||
(L.length < R.length ? L : R)
|
||||
: L[0] > R[0] ?
|
||||
L
|
||||
: R
|
||||
var res =
|
||||
// non-empty chunk and next...
|
||||
next[0] > 0 && l > 0 ?
|
||||
[l + next[0], chunk].concat(next.slice(1))
|
||||
// non-empty chunk and empty next...
|
||||
: l > 0 ?
|
||||
[l, chunk]
|
||||
// empty chunk...
|
||||
: next
|
||||
|
||||
// index...
|
||||
index[a] = index[a] || []
|
||||
index[a][b] = res
|
||||
|
||||
// index...
|
||||
var res = (index[a] || [])[b]
|
||||
if(res != null){
|
||||
return res
|
||||
}
|
||||
}
|
||||
|
||||
// get common chunk...
|
||||
var l = 0
|
||||
var chunk = []
|
||||
while(a+l < A.length
|
||||
&& b+l < B.length
|
||||
&& cmp(A[a+l], B[b+l])){
|
||||
chunk.push(A[a+l])
|
||||
l++
|
||||
}
|
||||
// discard small chunks...
|
||||
if(l < min_chunk){
|
||||
chunk = []
|
||||
l = 0
|
||||
}
|
||||
|
||||
// get next chunks...
|
||||
var L = A.length > a+l + min_chunk ?
|
||||
getCommonSections(
|
||||
A, B,
|
||||
l+a+1, l+b,
|
||||
min_chunk, cmp, index)
|
||||
: [0]
|
||||
var R = B.length > b+l + min_chunk ?
|
||||
getCommonSections(
|
||||
A, B,
|
||||
l+a, l+b+1,
|
||||
min_chunk, cmp, index)
|
||||
: [0]
|
||||
|
||||
// select the best chunk-set...
|
||||
// NOTE: we maximize the number of elements in a chunk set then
|
||||
// minimize the number of chunks per set...
|
||||
var next = L[0] == R[0] ?
|
||||
(L.length < R.length ? L : R)
|
||||
: L[0] > R[0] ?
|
||||
L
|
||||
: R
|
||||
var res = next[0] > 0 && l > 0 ?
|
||||
[l + next[0], chunk].concat(next.slice(1))
|
||||
: l > 0 ?
|
||||
[l, chunk]
|
||||
: next
|
||||
|
||||
// index...
|
||||
index[a] = index[a] || []
|
||||
index[a][b] = res
|
||||
|
||||
return res
|
||||
return _getCommonSections(0, 0)
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// XXX
|
||||
var getCommonSections2 = function(A, B, a, b, min_chunk, cmp){
|
||||
a = a || 0
|
||||
b = b || 0
|
||||
@ -200,6 +207,7 @@ var makeIndex = function(L){
|
||||
}, new Map()) }
|
||||
|
||||
|
||||
// XXX
|
||||
var getCommonSections3 = function(A, B){
|
||||
var A_index = makeIndex(A)
|
||||
var B_index = makeIndex(B)
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user