Commit Graph

2 Commits

Author SHA1 Message Date
Jun Wu
bdbf60f28d xdiff: backport upstream changes
Summary:
I did some extra xdiff changes in upstream, namely:

  - Remove unused features
  - Replace "long" (32-bit in MSVC) with int64_t to support large files
  - Add comment on some key variables

This backports them. It also includes Matt's fixes about Windows compatibility.

Reviewed By: ryanmce

Differential Revision: D7223939

fbshipit-source-id: 9287d5be22dae4ab41b05b3a4c160d836b5714a6
2018-04-13 21:51:48 -07:00
Jun Wu
65d9160c6f xdiff: vendor xdiff library from git
Summary:
Vendor git's xdiff library from git commit
d7c6c2369d7c6c2369ac21141b7c6cceaebc6414ec3da14ad using GPL2+ license.

There is another recent user report that hg diff generates suboptimal
result. It seems the fix to issue4074 isn't good enough. I crafted some
other interesting cases, and hg diff barely has any advantage compared with
gnu diffutils or git diff.

| testcase | gnu diffutils |      hg diff |   git diff |
|          |    lines time |   lines time | lines time |
| patience |        6 0.00 |     602 0.08 |     6 0.00 |
|   random |    91772 0.90 |  109462 0.70 | 91772 0.24 |
|     json |        2 0.03 | 1264814 1.81 |     2 0.29 |

"lines" means the size of the output, i.e. the count of "+/-" lines. "time"
means seconds needed to do the calculation. Both are the smaller the better.
"hg diff" counts Python startup overhead.

Git and GNU diffutils generate optimal results. For the "json" case, git can
have an optimization that does a scan for common prefix and suffix first,
and match them if the length is greater than half of the text. See
https://neil.fraser.name/news/2006/03/12/. That would make git the fastest
for all above cases.

About testcases:

patience:
Aiming for the weakness of the greedy "patience diff" algorithm.  Using
git's patience diff option would also get suboptimal result. Generated using
the Python script:

```
open('a', 'w').write('\n'.join(list('a' + 'x' * 300 + 'u' + 'x' * 700 + 'a\n')))
open('b', 'w').write('\n'.join(list('b' + 'x' * 700 + 'u' + 'x' * 300 + 'b\n')))
```

random:
Generated using the script in `test-issue4074.t`. It practically makes the
algorithm suffer. Impressively, git wins in both performance and diff
quality.

json:
The recent user reported case. It's a single line movement near the end of a
very large (800K lines) JSON file.

Reviewed By: ryanmce

Differential Revision: D7124455

fbshipit-source-id: 832651115da770f9d2ed5fdff2e200453c0013f8
2018-04-13 21:51:20 -07:00