View Javadoc

1   /**
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *     http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing, software
13   * distributed under the License is distributed on an "AS IS" BASIS,
14   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15   * See the License for the specific language governing permissions and
16   * limitations under the License.
17   */
18  package org.apache.hadoop.hbase.io.hfile;
19  
20  import org.apache.hadoop.classification.InterfaceAudience;
21  import org.apache.hadoop.hbase.io.HeapSize;
22  import org.apache.hadoop.hbase.io.encoding.DataBlockEncoding;
23  import org.apache.hadoop.hbase.util.Bytes;
24  import org.apache.hadoop.hbase.util.ClassSize;
25  
26  /**
27   * Cache Key for use with implementations of {@link BlockCache}
28   */
29  @InterfaceAudience.Private
30  public class BlockCacheKey implements HeapSize, java.io.Serializable {
31    private static final long serialVersionUID = -5199992013113130534L;
32    private final String hfileName;
33    private final long offset;
34    private final DataBlockEncoding encoding;
35  
36    public BlockCacheKey(String file, long offset, DataBlockEncoding encoding,
37        BlockType blockType) {
38      this.hfileName = file;
39      this.offset = offset;
40      // We add encoding to the cache key only for data blocks. If the block type
41      // is unknown (this should never be the case in production), we just use
42      // the provided encoding, because it might be a data block.
43      this.encoding = (encoding != null && (blockType == null
44        || blockType.isData())) ? encoding : DataBlockEncoding.NONE;
45    }
46  
47    /**
48     * Construct a new BlockCacheKey
49     * @param file The name of the HFile this block belongs to.
50     * @param offset Offset of the block into the file
51     */
52    public BlockCacheKey(String file, long offset) {
53      this(file, offset, DataBlockEncoding.NONE, null);
54    }
55  
56    @Override
57    public int hashCode() {
58      return hfileName.hashCode() * 127 + (int) (offset ^ (offset >>> 32)) +
59          encoding.ordinal() * 17;
60    }
61  
62    @Override
63    public boolean equals(Object o) {
64      if (o instanceof BlockCacheKey) {
65        BlockCacheKey k = (BlockCacheKey) o;
66        return offset == k.offset && encoding == k.encoding
67            && (hfileName == null ? k.hfileName == null : hfileName
68                .equals(k.hfileName));
69      } else {
70        return false;
71      }
72    }
73  
74    @Override
75    public String toString() {
76      return hfileName + "_" + offset
77          + (encoding == DataBlockEncoding.NONE ? "" : "_" + encoding);
78    }
79  
80    /**
81     * Strings have two bytes per character due to default Java Unicode encoding
82     * (hence length times 2).
83     */
84    @Override
85    public long heapSize() {
86      return ClassSize.align(ClassSize.OBJECT + 2 * hfileName.length() +
87          Bytes.SIZEOF_LONG + 2 * ClassSize.REFERENCE);
88    }
89  
90    // can't avoid this unfortunately
91    /**
92     * @return The hfileName portion of this cache key
93     */
94    public String getHfileName() {
95      return hfileName;
96    }
97  
98    public DataBlockEncoding getDataBlockEncoding() {
99      return encoding;
100   }
101 
102   public long getOffset() {
103     return offset;
104   }
105 }