ListDiff icon indicating copy to clipboard operation
ListDiff copied to clipboard

Bug: In an edge case, GenDiff will misidentify a Remove/Add as an Update

Open nesevis opened this issue 6 years ago • 1 comments

The edge case occurs while diffing a data source against a reversed version of itself.

Example: A list of 100 items with indices 0..99.

Link to code

if (i > 0 && j > 0 && match(x[i - 1], y[j - 1])) {
	GenDiff(c, x, y, i - 1, j - 1, match);
	Actions.Add(new ListDiffAction<S, D>(ListDiffActionType.Update, x[i - 1], y[j - 1]));
}

This check will return true while comparing original[99] with new[0].

My fix is just adding a check to see whether the indices match as well:

if (i > 0 && j > 0 && sourceIdx == destIdx && match(x[i - 1], y[j - 1]))
	GenDiff(c, x, y, i - 1, j - 1, match);
	Actions.Add(new ListDiffAction<S, D>(ListDiffActionType.Update, x[i - 1], y[j - 1]));
}

nesevis avatar Oct 26 '19 21:10 nesevis

Fascinating, what a find. I'm going to have to add a test case to fully wrap my head around it. Your solution seems fine but I just merged an optimization that's going to make the arithmetic tricky. Either way, just complaining, great find, thanks.

praeclarum avatar Mar 01 '20 02:03 praeclarum