Merge "Define DiffAlgorithm as an abstract function"
This commit is contained in:
commit
207ab8b8f5
|
@ -384,9 +384,9 @@ private void scanProjectCommits(Project proj, RevCommit start)
|
||||||
else
|
else
|
||||||
oldImage = new byte[0];
|
oldImage = new byte[0];
|
||||||
|
|
||||||
EditList edits = new MyersDiff<RawText>(
|
EditList edits = MyersDiff.INSTANCE.diff(
|
||||||
RawTextComparator.DEFAULT, new RawText(oldImage),
|
RawTextComparator.DEFAULT, new RawText(oldImage),
|
||||||
new RawText(openBlob(1))).getEdits();
|
new RawText(openBlob(1)));
|
||||||
for (Edit e : edits)
|
for (Edit e : edits)
|
||||||
addedLines += e.getEndB() - e.getBeginB();
|
addedLines += e.getEndB() - e.getBeginB();
|
||||||
}
|
}
|
||||||
|
|
|
@ -164,14 +164,14 @@ private PerfData test(int characters) {
|
||||||
CharArray ac = new CharArray(a);
|
CharArray ac = new CharArray(a);
|
||||||
CharArray bc = new CharArray(b);
|
CharArray bc = new CharArray(b);
|
||||||
CharCmp cmp = new CharCmp();
|
CharCmp cmp = new CharCmp();
|
||||||
MyersDiff<CharArray> myersDiff = null;
|
int D = 0;
|
||||||
int cpuTimeChanges = 0;
|
int cpuTimeChanges = 0;
|
||||||
long lastReadout = 0;
|
long lastReadout = 0;
|
||||||
long interimTime = 0;
|
long interimTime = 0;
|
||||||
int repetitions = 0;
|
int repetitions = 0;
|
||||||
stopwatch.start();
|
stopwatch.start();
|
||||||
while (cpuTimeChanges < minCPUTimerTicks && interimTime < longTaskBoundary) {
|
while (cpuTimeChanges < minCPUTimerTicks && interimTime < longTaskBoundary) {
|
||||||
myersDiff = new MyersDiff<CharArray>(cmp, ac, bc);
|
D = MyersDiff.INSTANCE.diff(cmp, ac, bc).size();
|
||||||
repetitions++;
|
repetitions++;
|
||||||
interimTime = stopwatch.readout();
|
interimTime = stopwatch.readout();
|
||||||
if (interimTime != lastReadout) {
|
if (interimTime != lastReadout) {
|
||||||
|
@ -181,7 +181,7 @@ private PerfData test(int characters) {
|
||||||
}
|
}
|
||||||
ret.runningTime = stopwatch.stop() / repetitions;
|
ret.runningTime = stopwatch.stop() / repetitions;
|
||||||
ret.N = ac.size() + bc.size();
|
ret.N = ac.size() + bc.size();
|
||||||
ret.D = myersDiff.getEdits().size();
|
ret.D = D;
|
||||||
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
|
@ -63,9 +63,9 @@ public void testSimple() {
|
||||||
}
|
}
|
||||||
|
|
||||||
public void assertDiff(String a, String b, String edits) {
|
public void assertDiff(String a, String b, String edits) {
|
||||||
MyersDiff diff = new MyersDiff<CharArray>(new CharCmp(),
|
EditList editList = MyersDiff.INSTANCE.diff(new CharCmp(),
|
||||||
toCharArray(a), toCharArray(b));
|
toCharArray(a), toCharArray(b));
|
||||||
assertEquals(edits, toString(diff.getEdits()));
|
assertEquals(edits, toString(editList));
|
||||||
}
|
}
|
||||||
|
|
||||||
private static String toString(EditList list) {
|
private static String toString(EditList list) {
|
||||||
|
|
|
@ -0,0 +1,79 @@
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2010, Google Inc.
|
||||||
|
* and other copyright owners as documented in the project's IP log.
|
||||||
|
*
|
||||||
|
* This program and the accompanying materials are made available
|
||||||
|
* under the terms of the Eclipse Distribution License v1.0 which
|
||||||
|
* accompanies this distribution, is reproduced below, and is
|
||||||
|
* available at http://www.eclipse.org/org/documents/edl-v10.php
|
||||||
|
*
|
||||||
|
* All rights reserved.
|
||||||
|
*
|
||||||
|
* Redistribution and use in source and binary forms, with or
|
||||||
|
* without modification, are permitted provided that the following
|
||||||
|
* conditions are met:
|
||||||
|
*
|
||||||
|
* - Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer.
|
||||||
|
*
|
||||||
|
* - Redistributions in binary form must reproduce the above
|
||||||
|
* copyright notice, this list of conditions and the following
|
||||||
|
* disclaimer in the documentation and/or other materials provided
|
||||||
|
* with the distribution.
|
||||||
|
*
|
||||||
|
* - Neither the name of the Eclipse Foundation, Inc. nor the
|
||||||
|
* names of its contributors may be used to endorse or promote
|
||||||
|
* products derived from this software without specific prior
|
||||||
|
* written permission.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
|
||||||
|
* CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||||
|
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||||
|
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
|
||||||
|
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
|
||||||
|
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||||
|
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
|
||||||
|
* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||||
|
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||||
|
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package org.eclipse.jgit.diff;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Compares two {@link Sequence}s to create an {@link EditList} of changes.
|
||||||
|
*
|
||||||
|
* An algorithm's {@code diff} method must be callable from concurrent threads
|
||||||
|
* without data collisions. This permits some algorithms to use a singleton
|
||||||
|
* pattern, with concurrent invocations using the same singleton. Other
|
||||||
|
* algorithms may support parameterization, in which case the caller can create
|
||||||
|
* a unique instance per thread.
|
||||||
|
*/
|
||||||
|
public interface DiffAlgorithm {
|
||||||
|
/**
|
||||||
|
* Compare two sequences and identify a list of edits between them.
|
||||||
|
*
|
||||||
|
* @param <S>
|
||||||
|
* type of sequence being compared.
|
||||||
|
* @param <C>
|
||||||
|
* type of comparator to evaluate the sequence elements.
|
||||||
|
* @param cmp
|
||||||
|
* the comparator supplying the element equivalence function.
|
||||||
|
* @param a
|
||||||
|
* the first (also known as old or pre-image) sequence. Edits
|
||||||
|
* returned by this algorithm will reference indexes using the
|
||||||
|
* 'A' side: {@link Edit#getBeginA()}, {@link Edit#getEndA()}.
|
||||||
|
* @param b
|
||||||
|
* the second (also known as new or post-image) sequence. Edits
|
||||||
|
* returned by this algorithm will reference indexes using the
|
||||||
|
* 'B' side: {@link Edit#getBeginB()}, {@link Edit#getEndB()}.
|
||||||
|
* @return a modifiable edit list comparing the two sequences. If empty, the
|
||||||
|
* sequences are identical according to {@code cmp}'s rules. The
|
||||||
|
* result list is never null.
|
||||||
|
*/
|
||||||
|
public <S extends Sequence, C extends SequenceComparator<? super S>> EditList diff(
|
||||||
|
C cmp, S a, S b);
|
||||||
|
}
|
|
@ -118,6 +118,8 @@ public class DiffFormatter {
|
||||||
|
|
||||||
private int abbreviationLength = 7;
|
private int abbreviationLength = 7;
|
||||||
|
|
||||||
|
private DiffAlgorithm diffAlgorithm = MyersDiff.INSTANCE;
|
||||||
|
|
||||||
private RawTextComparator comparator = RawTextComparator.DEFAULT;
|
private RawTextComparator comparator = RawTextComparator.DEFAULT;
|
||||||
|
|
||||||
private int binaryFileThreshold = DEFAULT_BINARY_FILE_THRESHOLD;
|
private int binaryFileThreshold = DEFAULT_BINARY_FILE_THRESHOLD;
|
||||||
|
@ -206,6 +208,17 @@ public void setAbbreviationLength(final int count) {
|
||||||
abbreviationLength = count;
|
abbreviationLength = count;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the algorithm that constructs difference output.
|
||||||
|
*
|
||||||
|
* @param alg
|
||||||
|
* the algorithm to produce text file differences.
|
||||||
|
* @see MyersDiff#INSTANCE
|
||||||
|
*/
|
||||||
|
public void setDiffAlgorithm(DiffAlgorithm alg) {
|
||||||
|
diffAlgorithm = alg;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the line equivalence function for text file differences.
|
* Set the line equivalence function for text file differences.
|
||||||
*
|
*
|
||||||
|
@ -893,7 +906,7 @@ private FormatResult createFormatResult(DiffEntry ent) throws IOException,
|
||||||
}
|
}
|
||||||
|
|
||||||
private EditList diff(RawText a, RawText b) {
|
private EditList diff(RawText a, RawText b) {
|
||||||
return new MyersDiff<RawText>(comparator, a, b).getEdits();
|
return diffAlgorithm.diff(comparator, a, b);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void assertHaveRepository() {
|
private void assertHaveRepository() {
|
||||||
|
|
|
@ -106,13 +106,21 @@
|
||||||
* type of sequence.
|
* type of sequence.
|
||||||
*/
|
*/
|
||||||
public class MyersDiff<S extends Sequence> {
|
public class MyersDiff<S extends Sequence> {
|
||||||
|
/** Singleton instance of MyersDiff. */
|
||||||
|
public static final DiffAlgorithm INSTANCE = new DiffAlgorithm() {
|
||||||
|
public <S extends Sequence, C extends SequenceComparator<? super S>> EditList diff(
|
||||||
|
C cmp, S a, S b) {
|
||||||
|
return new MyersDiff<S>(cmp, a, b).getEdits();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The list of edits found during the last call to {@link #calculateEdits()}
|
* The list of edits found during the last call to {@link #calculateEdits()}
|
||||||
*/
|
*/
|
||||||
protected EditList edits;
|
protected EditList edits;
|
||||||
|
|
||||||
/** Comparison function for sequences. */
|
/** Comparison function for sequences. */
|
||||||
protected SequenceComparator<S> cmp;
|
protected SequenceComparator<? super S> cmp;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The first text to be compared. Referred to as "Text A" in the comments
|
* The first text to be compared. Referred to as "Text A" in the comments
|
||||||
|
@ -124,14 +132,7 @@ public class MyersDiff<S extends Sequence> {
|
||||||
*/
|
*/
|
||||||
protected S b;
|
protected S b;
|
||||||
|
|
||||||
/**
|
private MyersDiff(SequenceComparator<? super S> cmp, S a, S b) {
|
||||||
* The only constructor
|
|
||||||
*
|
|
||||||
* @param cmp comparison method for this execution.
|
|
||||||
* @param a the text A which should be compared
|
|
||||||
* @param b the text B which should be compared
|
|
||||||
*/
|
|
||||||
public MyersDiff(SequenceComparator<S> cmp, S a, S b) {
|
|
||||||
this.cmp = cmp;
|
this.cmp = cmp;
|
||||||
this.a = a;
|
this.a = a;
|
||||||
this.b = b;
|
this.b = b;
|
||||||
|
|
|
@ -90,9 +90,9 @@ public static <S extends Sequence> MergeResult<S> merge(
|
||||||
sequences.add(ours);
|
sequences.add(ours);
|
||||||
sequences.add(theirs);
|
sequences.add(theirs);
|
||||||
MergeResult result = new MergeResult<S>(sequences);
|
MergeResult result = new MergeResult<S>(sequences);
|
||||||
EditList oursEdits = new MyersDiff<S>(cmp, base, ours).getEdits();
|
EditList oursEdits = MyersDiff.INSTANCE.diff(cmp, base, ours);
|
||||||
Iterator<Edit> baseToOurs = oursEdits.iterator();
|
Iterator<Edit> baseToOurs = oursEdits.iterator();
|
||||||
EditList theirsEdits = new MyersDiff<S>(cmp, base, theirs).getEdits();
|
EditList theirsEdits = MyersDiff.INSTANCE.diff(cmp, base, theirs);
|
||||||
Iterator<Edit> baseToTheirs = theirsEdits.iterator();
|
Iterator<Edit> baseToTheirs = theirsEdits.iterator();
|
||||||
int current = 0; // points to the next line (first line is 0) of base
|
int current = 0; // points to the next line (first line is 0) of base
|
||||||
// which was not handled yet
|
// which was not handled yet
|
||||||
|
|
Loading…
Reference in New Issue