Monday 31 March 2014

A better diff system than DiffUtils?

After looking around with some help, the help guided me to DiffMatchPatch ( google-diff-match-patch ), as the name says, a diff system from Google.

It was decided to use this instead of DiffUtils because you can compare two Strings instead of two List<String> and the deltas can also be stored as a single text String which is quite a bit smaller storage needs than storing the DiffUtils.Patch object.

So as a new example of how to use DiffMatchPatch, I've rewritten the code from the previous blog post to use it with the same JUnit test.

Note that "firstVersion" and "secondVersion" Strings are the same value as they were in the previous blog post.

Example:


@Test
public void javaDiffTests()
{
 String firstVersion = getStringVersionOne();
 String secondVersion = getStringVersionTwo();

 String result = getDiffMatchPatch(firstVersion, secondVersion);
 if(!result.equals(secondVersion))
 {
  fail("diff test has failed, they are not the same. Check the getDiffUtils() method");
 }
}

public String getDiffMatchPatch(String firstVersion, String secondVersion)
{
 DiffMatchPatch dmp = new DiffMatchPatch();
 LinkedList<DiffMatchPatch.Diff> result = dmp.diff_main(firstVersion, secondVersion);

 LinkedList<DiffMatchPatch.Patch> patches = dmp.patch_make(result);

 String patchesText = dmp.patch_toText(patches);//This is to prove that you can store your diffs as a single String
 LinkedList<DiffMatchPatch.Patch> revivedFromTextPatches = (LinkedList<DiffMatchPatch.Patch>) dmp.patch_fromText(patchesText);

 Object[] patchedResultObjects = dmp.patch_apply(revivedFromTextPatches, firstVersion);

 boolean[] passRate = (boolean[]) patchedResultObjects[1];//"...The second element is an array of true/false values indicating which of the patches were successfully applied."

 for(boolean b : passRate)
 {
  if(!b)//we only want to proceed if all patches were successfully applied
   return null;
 }

 String merge = (String) patchedResultObjects[0];//"...The first element of the return value is the newly patched text."

 return merge;
}


Links:

The site for DiffMatchPatch is here .
You can find the Maven dependency for DiffMatchPatch from its forked project DiffPatch here .

No comments:

Post a Comment