Skip to content

Commit 4f6f8db

Browse files
committed
fixes #14
1 parent 573460d commit 4f6f8db

File tree

3 files changed

+59
-23
lines changed

3 files changed

+59
-23
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ But it can easily replaced by any other which is better for handing your texts.
5353
* Version 2.1-SNAPSHOT
5454
* included checkstyle source code conventions
5555
* groupid changed to **com.github.wumpz**, due to maven central releasing
56+
* allow configurable splitting of lines to define the blocks to compare (words, characters, phrases).
5657
* Version 2.0
5758
* switch to maven and removed other artifacts
5859
* changed groupid to **com.github.java-diff-utils** due to different forks at github

src/main/java/com/github/difflib/text/DiffRowGenerator.java

Lines changed: 35 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -47,16 +47,34 @@
4747
* </code>
4848
*/
4949
public class DiffRowGenerator {
50-
50+
public static final Pattern SPLIT_BY_WORD_PATTERN = Pattern.compile("\\s+|[,.\\[\\](){}/\\\\*+\\-#]");
51+
5152
public static final BiPredicate<String, String> IGNORE_WHITESPACE_EQUALIZER = (original, revised)
5253
-> original.trim().replaceAll("\\s+", " ").equals(revised.trim().replaceAll("\\s+", " "));
54+
5355
public static final BiPredicate<String, String> DEFAULT_EQUALIZER = Object::equals;
54-
private static final Pattern SPLIT_PATTERN = Pattern.compile("\\s+|[,.\\[\\](){}/\\\\*+\\-#]");
56+
57+
/**
58+
* Splitting lines by word to achieve word by word diff checking.
59+
*/
60+
public static final Function<String, List<String>> SPLITTER_BY_WORD = line -> splitStringPreserveDelimiter(line, SPLIT_BY_WORD_PATTERN);
61+
62+
/**
63+
* Splitting lines by character to achieve char by char diff checking.
64+
*/
65+
public static final Function<String, List<String>> SPLITTER_BY_CHARACTER = line -> {
66+
List<String> list = new ArrayList<>(line.length());
67+
for (Character character : line.toCharArray()) {
68+
list.add(character.toString());
69+
}
70+
return list;
71+
};
72+
5573
private final boolean showInlineDiffs;
5674
private final boolean ignoreWhiteSpaces;
5775
private final Function<Boolean, String> oldTag;
5876
private final Function<Boolean, String> newTag;
59-
private final boolean inlineDiffByWord;
77+
private final Function<String, List<String>> inlineDiffSplitter;
6078
private final int columnWidth;
6179
private final BiPredicate<String, String> equalizer;
6280
private final boolean mergeOriginalRevised;
@@ -78,8 +96,8 @@ public static class Builder {
7896

7997
private int columnWidth = 0;
8098
private boolean mergeOriginalRevised = false;
81-
private boolean inlineDiffByWord = false;
8299
private boolean reportLinesUnchanged = false;
100+
private Function<String, List<String>> inlineDiffSplitter = SPLITTER_BY_CHARACTER;
83101

84102
private Builder() {
85103
}
@@ -177,7 +195,13 @@ public Builder mergeOriginalRevised(boolean mergeOriginalRevised) {
177195
* deliver no in word changes.
178196
*/
179197
public Builder inlineDiffByWord(boolean inlineDiffByWord) {
180-
this.inlineDiffByWord = inlineDiffByWord;
198+
inlineDiffSplitter = inlineDiffByWord?SPLITTER_BY_WORD:SPLITTER_BY_CHARACTER;
199+
return this;
200+
}
201+
202+
203+
public Builder inlineDiffBySplitter(Function<String, List<String>> inlineDiffSplitter) {
204+
this.inlineDiffSplitter = inlineDiffSplitter;
181205
return this;
182206
}
183207
}
@@ -193,9 +217,11 @@ private DiffRowGenerator(Builder builder) {
193217
newTag = builder.newTag;
194218
columnWidth = builder.columnWidth;
195219
mergeOriginalRevised = builder.mergeOriginalRevised;
196-
inlineDiffByWord = builder.inlineDiffByWord;
220+
inlineDiffSplitter = builder.inlineDiffSplitter;
197221
equalizer = ignoreWhiteSpaces ? IGNORE_WHITESPACE_EQUALIZER : DEFAULT_EQUALIZER;
198222
reportLinesUnchanged = builder.reportLinesUnchanged;
223+
224+
Objects.requireNonNull(inlineDiffSplitter);
199225
}
200226

201227
/**
@@ -318,19 +344,8 @@ private List<DiffRow> generateInlineDiffs(Delta<String> delta) throws DiffExcept
318344
String joinedOrig = String.join("\n", orig);
319345
String joinedRev = String.join("\n", rev);
320346

321-
if (inlineDiffByWord) {
322-
origList = splitStringPreserveDelimiter(joinedOrig);
323-
revList = splitStringPreserveDelimiter(joinedRev);
324-
} else {
325-
origList = new ArrayList<>(joinedOrig.length());
326-
revList = new ArrayList<>(joinedRev.length());
327-
for (Character character : joinedOrig.toCharArray()) {
328-
origList.add(character.toString());
329-
}
330-
for (Character character : joinedRev.toCharArray()) {
331-
revList.add(character.toString());
332-
}
333-
}
347+
origList = inlineDiffSplitter.apply(joinedOrig);
348+
revList = inlineDiffSplitter.apply(joinedRev);
334349

335350
List<Delta<String>> inlineDeltas = DiffUtils.diff(origList, revList).getDeltas();
336351

@@ -404,7 +419,7 @@ public static void wrapInTag(List<String> sequence, int startPosition,
404419
sequence.add(endPosition, generator.apply(false));
405420
}
406421

407-
protected final static List<String> splitStringPreserveDelimiter(String str) {
422+
protected final static List<String> splitStringPreserveDelimiter(String str, Pattern SPLIT_PATTERN) {
408423
List<String> list = new ArrayList<>();
409424
if (str != null) {
410425
Matcher matcher = SPLIT_PATTERN.matcher(str);

src/test/java/com/github/difflib/text/DiffRowGeneratorTest.java

Lines changed: 23 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import com.github.difflib.algorithm.DiffException;
44
import java.util.Arrays;
55
import java.util.List;
6+
import java.util.regex.Pattern;
67
import static org.junit.Assert.assertEquals;
78
import static org.junit.Assert.assertTrue;
89
import org.junit.Test;
@@ -182,22 +183,22 @@ public void testGeneratorWithMergeByWord5() throws DiffException {
182183

183184
@Test
184185
public void testSplitString() {
185-
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test,test2");
186+
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test,test2", DiffRowGenerator.SPLIT_BY_WORD_PATTERN);
186187
assertEquals(3, list.size());
187188
assertEquals("[test, ,, test2]", list.toString());
188189
}
189190

190191
@Test
191192
public void testSplitString2() {
192-
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test , test2");
193+
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test , test2", DiffRowGenerator.SPLIT_BY_WORD_PATTERN);
193194
System.out.println(list);
194195
assertEquals(5, list.size());
195196
assertEquals("[test, , ,, , test2]", list.toString());
196197
}
197198

198199
@Test
199200
public void testSplitString3() {
200-
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test,test2,");
201+
List<String> list = DiffRowGenerator.splitStringPreserveDelimiter("test,test2,", DiffRowGenerator.SPLIT_BY_WORD_PATTERN);
201202
System.out.println(list);
202203
assertEquals(4, list.size());
203204
assertEquals("[test, ,, test2, ,]", list.toString());
@@ -262,4 +263,23 @@ public void testGeneratorUnchanged() throws DiffException {
262263
assertEquals("[CHANGE, ,]", rows.get(1).toString());
263264
assertEquals("[EQUAL,other,other]", rows.get(2).toString());
264265
}
266+
267+
@Test
268+
public void testGeneratorIssue14() throws DiffException {
269+
DiffRowGenerator generator = DiffRowGenerator.create()
270+
.showInlineDiffs(true)
271+
.mergeOriginalRevised(true)
272+
.inlineDiffBySplitter(line -> DiffRowGenerator.splitStringPreserveDelimiter(line, Pattern.compile(",")))
273+
.oldTag(f -> "~")
274+
.newTag(f -> "**")
275+
.build();
276+
List<DiffRow> rows = generator.generateDiffRows(
277+
Arrays.asList("J. G. Feldstein, Chair"),
278+
Arrays.asList("T. P. Pastor, Chair"));
279+
280+
System.out.println(rows.get(0).getOldLine());
281+
282+
assertEquals(1, rows.size());
283+
assertEquals("~J. G. Feldstein~**T. P. Pastor**, Chair", rows.get(0).getOldLine());
284+
}
265285
}

0 commit comments

Comments
 (0)