1 /*******************************************************************************
2 * Copyright (c) 2007, 2011 IBM Corporation and others.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
9 * IBM Corporation - initial API and implementation
10 *******************************************************************************/
11 package org.eclipse.jdt.internal.ui.text;
13 import java.util.ArrayList;
14 import java.util.Arrays;
16 import org.eclipse.jface.text.BadLocationException;
17 import org.eclipse.jface.text.IDocument;
18 import org.eclipse.jface.text.IRegion;
20 import org.eclipse.compare.rangedifferencer.IRangeComparator;
22 import org.eclipse.jdt.internal.ui.JavaPlugin;
26 * This implementation of <code>IRangeComparator</code> compares lines of a document.
27 * The lines are compared using a DJB hash function.
31 public class LineComparator implements IRangeComparator {
33 private final IDocument fDocument;
34 private final ArrayList<Integer> fHashes;
37 * Create a line comparator for the given document.
39 * @param document the document
41 public LineComparator(IDocument document) {
44 Integer[] nulls= new Integer[fDocument.getNumberOfLines()];
45 fHashes= new ArrayList<Integer>(Arrays.asList(nulls));
49 * @see org.eclipse.compare.rangedifferencer.IRangeComparator#getRangeCount()
51 public int getRangeCount() {
52 return fDocument.getNumberOfLines();
56 * @see org.eclipse.compare.rangedifferencer.IRangeComparator#rangesEqual(int, org.eclipse.compare.rangedifferencer.IRangeComparator, int)
58 public boolean rangesEqual(int thisIndex, IRangeComparator other, int otherIndex) {
60 return getHash(thisIndex).equals(((LineComparator) other).getHash(otherIndex));
61 } catch (BadLocationException e) {
68 * @see org.eclipse.compare.rangedifferencer.IRangeComparator#skipRangeComparison(int, int, org.eclipse.compare.rangedifferencer.IRangeComparator)
70 public boolean skipRangeComparison(int length, int maxLength, IRangeComparator other) {
75 * @param line the number of the line in the document to get the hash for
76 * @return the hash of the line
77 * @throws BadLocationException if the line number is invalid
79 private Integer getHash(int line) throws BadLocationException {
80 Integer hash= fHashes.get(line);
82 IRegion lineRegion= fDocument.getLineInformation(line);
83 String lineContents= fDocument.get(lineRegion.getOffset(), lineRegion.getLength());
84 hash= new Integer(computeDJBHash(lineContents));
85 fHashes.set(line, hash);
92 * Compute a hash using the DJB hash algorithm
94 * @param string the string for which to compute a hash
95 * @return the DJB hash value of the string
97 private int computeDJBHash(String string) {
99 int len= string.length();
100 for (int i= 0; i < len; i++) {
101 char ch= string.charAt(i);
102 hash= (hash << 5) + hash + ch;