001    /*
002     * Sonar, open source software quality management tool.
003     * Copyright (C) 2008-2011 SonarSource
004     * mailto:contact AT sonarsource DOT com
005     *
006     * Sonar is free software; you can redistribute it and/or
007     * modify it under the terms of the GNU Lesser General Public
008     * License as published by the Free Software Foundation; either
009     * version 3 of the License, or (at your option) any later version.
010     *
011     * Sonar is distributed in the hope that it will be useful,
012     * but WITHOUT ANY WARRANTY; without even the implied warranty of
013     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
014     * Lesser General Public License for more details.
015     *
016     * You should have received a copy of the GNU Lesser General Public
017     * License along with Sonar; if not, write to the Free Software
018     * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02
019     */
020    package org.sonar.duplications.block;
021    
022    /**
023     * Represents part of source code between two lines.
024     * If two blocks have the same {@link #getBlockHash() hash}, then we assume that there is a duplication in a code, which they represent.
025     */
026    public final class Block {
027    
028      private final String resourceId;
029      private final ByteArray blockHash;
030      private final int indexInFile;
031      private final int firstLineNumber;
032      private final int lastLineNumber;
033    
034      /**
035       * Cache for hash code.
036       */
037      private int hash;
038    
039      public Block(String resourceId, ByteArray blockHash, int indexInFile, int firstLineNumber, int lastLineNumber) {
040        this.resourceId = resourceId;
041        this.blockHash = blockHash;
042        this.indexInFile = indexInFile;
043        this.firstLineNumber = firstLineNumber;
044        this.lastLineNumber = lastLineNumber;
045      }
046    
047      public Block(int indexInFile, int firstLineNumber, int lastLineNumber, String resourceId, String hash) {
048        this(resourceId, new ByteArray(hash), indexInFile, firstLineNumber, lastLineNumber);
049      }
050    
051      public String getHashHex() {
052        return getBlockHash().toString();
053      }
054    
055      public String getResourceId() {
056        return resourceId;
057      }
058    
059      public ByteArray getBlockHash() {
060        return blockHash;
061      }
062    
063      public int getIndexInFile() {
064        return indexInFile;
065      }
066    
067      public int getFirstLineNumber() {
068        return firstLineNumber;
069      }
070    
071      public int getLastLineNumber() {
072        return lastLineNumber;
073      }
074    
075      @Override
076      public boolean equals(Object obj) {
077        if (!(obj instanceof Block)) {
078          return false;
079        }
080        Block other = (Block) obj;
081        return resourceId.equals(other.resourceId)
082            && blockHash.equals(other.blockHash)
083            && indexInFile == other.indexInFile
084            && firstLineNumber == other.firstLineNumber
085            && lastLineNumber == other.lastLineNumber;
086      }
087    
088      @Override
089      public int hashCode() {
090        int h = hash;
091        if (h == 0) {
092          h = resourceId.hashCode();
093          h = 31 * h + blockHash.hashCode();
094          h = 31 * h + indexInFile;
095          h = 31 * h + firstLineNumber;
096          h = 31 * h + lastLineNumber;
097          hash = h;
098        }
099        return h;
100      }
101    
102      @Override
103      public String toString() {
104        return "'" + resourceId + "'[" + indexInFile + "|" + firstLineNumber + "-" + lastLineNumber + "]:" + blockHash;
105      }
106    
107    }