SequenceComparator.java

  1. /*
  2.  * Copyright (C) 2010, Google Inc. and others
  3.  *
  4.  * This program and the accompanying materials are made available under the
  5.  * terms of the Eclipse Distribution License v. 1.0 which is available at
  6.  * https://www.eclipse.org/org/documents/edl-v10.php.
  7.  *
  8.  * SPDX-License-Identifier: BSD-3-Clause
  9.  */

  10. package org.eclipse.jgit.diff;

  11. /**
  12.  * Equivalence function for a {@link org.eclipse.jgit.diff.Sequence} compared by
  13.  * difference algorithm.
  14.  * <p>
  15.  * Difference algorithms can use a comparator to compare portions of two
  16.  * sequences and discover the minimal edits required to transform from one
  17.  * sequence to the other sequence.
  18.  * <p>
  19.  * Indexes within a sequence are zero-based.
  20.  *
  21.  * @param <S>
  22.  *            type of sequence the comparator supports.
  23.  */
  24. public abstract class SequenceComparator<S extends Sequence> {
  25.     /**
  26.      * Compare two items to determine if they are equivalent.
  27.      *
  28.      * It is permissible to compare sequence {@code a} with itself (by passing
  29.      * {@code a} again in position {@code b}).
  30.      *
  31.      * @param a
  32.      *            the first sequence.
  33.      * @param ai
  34.      *            item of {@code ai} to compare.
  35.      * @param b
  36.      *            the second sequence.
  37.      * @param bi
  38.      *            item of {@code bi} to compare.
  39.      * @return true if the two items are identical according to this function's
  40.      *         equivalence rule.
  41.      */
  42.     public abstract boolean equals(S a, int ai, S b, int bi);

  43.     /**
  44.      * Get a hash value for an item in a sequence.
  45.      *
  46.      * If two items are equal according to this comparator's
  47.      * {@link #equals(Sequence, int, Sequence, int)} method, then this hash
  48.      * method must produce the same integer result for both items.
  49.      *
  50.      * It is not required for two items to have different hash values if they
  51.      * are unequal according to the {@code equals()} method.
  52.      *
  53.      * @param seq
  54.      *            the sequence.
  55.      * @param ptr
  56.      *            the item to obtain the hash for.
  57.      * @return hash the hash value.
  58.      */
  59.     public abstract int hash(S seq, int ptr);

  60.     /**
  61.      * Modify the edit to remove common leading and trailing items.
  62.      *
  63.      * The supplied edit {@code e} is reduced in size by moving the beginning A
  64.      * and B points so the edit does not cover any items that are in common
  65.      * between the two sequences. The ending A and B points are also shifted to
  66.      * remove common items from the end of the region.
  67.      *
  68.      * @param a
  69.      *            the first sequence.
  70.      * @param b
  71.      *            the second sequence.
  72.      * @param e
  73.      *            the edit to start with and update.
  74.      * @return {@code e} if it was updated in-place, otherwise a new edit
  75.      *         containing the reduced region.
  76.      */
  77.     public Edit reduceCommonStartEnd(S a, S b, Edit e) {
  78.         // Skip over items that are common at the start.
  79.         //
  80.         while (e.beginA < e.endA && e.beginB < e.endB
  81.                 && equals(a, e.beginA, b, e.beginB)) {
  82.             e.beginA++;
  83.             e.beginB++;
  84.         }

  85.         // Skip over items that are common at the end.
  86.         //
  87.         while (e.beginA < e.endA && e.beginB < e.endB
  88.                 && equals(a, e.endA - 1, b, e.endB - 1)) {
  89.             e.endA--;
  90.             e.endB--;
  91.         }

  92.         return e;
  93.     }
  94. }