001/** 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.io; 019 020import java.io.DataInput; 021import java.io.DataOutput; 022import java.io.IOException; 023import java.util.Collection; 024import java.util.Comparator; 025import java.util.Map; 026import java.util.Set; 027import java.util.SortedMap; 028import java.util.TreeMap; 029 030import org.apache.hadoop.classification.InterfaceAudience; 031import org.apache.hadoop.classification.InterfaceStability; 032import org.apache.hadoop.util.ReflectionUtils; 033 034/** 035 * A Writable SortedMap. 036 */ 037@InterfaceAudience.Public 038@InterfaceStability.Stable 039public class SortedMapWritable extends AbstractMapWritable 040 implements SortedMap<WritableComparable, Writable> { 041 042 private SortedMap<WritableComparable, Writable> instance; 043 044 /** default constructor. */ 045 public SortedMapWritable() { 046 super(); 047 this.instance = new TreeMap<WritableComparable, Writable>(); 048 } 049 050 /** 051 * Copy constructor. 052 * 053 * @param other the map to copy from 054 */ 055 public SortedMapWritable(SortedMapWritable other) { 056 this(); 057 copy(other); 058 } 059 060 @Override 061 public Comparator<? super WritableComparable> comparator() { 062 // Returning null means we use the natural ordering of the keys 063 return null; 064 } 065 066 @Override 067 public WritableComparable firstKey() { 068 return instance.firstKey(); 069 } 070 071 @Override 072 public SortedMap<WritableComparable, Writable> 073 headMap(WritableComparable toKey) { 074 075 return instance.headMap(toKey); 076 } 077 078 @Override 079 public WritableComparable lastKey() { 080 return instance.lastKey(); 081 } 082 083 @Override 084 public SortedMap<WritableComparable, Writable> 085 subMap(WritableComparable fromKey, WritableComparable toKey) { 086 087 return instance.subMap(fromKey, toKey); 088 } 089 090 @Override 091 public SortedMap<WritableComparable, Writable> 092 tailMap(WritableComparable fromKey) { 093 094 return instance.tailMap(fromKey); 095 } 096 097 @Override 098 public void clear() { 099 instance.clear(); 100 } 101 102 @Override 103 public boolean containsKey(Object key) { 104 return instance.containsKey(key); 105 } 106 107 @Override 108 public boolean containsValue(Object value) { 109 return instance.containsValue(value); 110 } 111 112 @Override 113 public Set<java.util.Map.Entry<WritableComparable, Writable>> entrySet() { 114 return instance.entrySet(); 115 } 116 117 @Override 118 public Writable get(Object key) { 119 return instance.get(key); 120 } 121 122 @Override 123 public boolean isEmpty() { 124 return instance.isEmpty(); 125 } 126 127 @Override 128 public Set<WritableComparable> keySet() { 129 return instance.keySet(); 130 } 131 132 @Override 133 public Writable put(WritableComparable key, Writable value) { 134 addToMap(key.getClass()); 135 addToMap(value.getClass()); 136 return instance.put(key, value); 137 } 138 139 @Override 140 public void putAll(Map<? extends WritableComparable, ? extends Writable> t) { 141 for (Map.Entry<? extends WritableComparable, ? extends Writable> e: 142 t.entrySet()) { 143 144 put(e.getKey(), e.getValue()); 145 } 146 } 147 148 @Override 149 public Writable remove(Object key) { 150 return instance.remove(key); 151 } 152 153 @Override 154 public int size() { 155 return instance.size(); 156 } 157 158 @Override 159 public Collection<Writable> values() { 160 return instance.values(); 161 } 162 163 @SuppressWarnings("unchecked") 164 @Override 165 public void readFields(DataInput in) throws IOException { 166 super.readFields(in); 167 168 // Read the number of entries in the map 169 170 int entries = in.readInt(); 171 172 // Then read each key/value pair 173 174 for (int i = 0; i < entries; i++) { 175 WritableComparable key = 176 (WritableComparable) ReflectionUtils.newInstance(getClass( 177 in.readByte()), getConf()); 178 179 key.readFields(in); 180 181 Writable value = (Writable) ReflectionUtils.newInstance(getClass( 182 in.readByte()), getConf()); 183 184 value.readFields(in); 185 instance.put(key, value); 186 } 187 } 188 189 @Override 190 public void write(DataOutput out) throws IOException { 191 super.write(out); 192 193 // Write out the number of entries in the map 194 195 out.writeInt(instance.size()); 196 197 // Then write out each key/value pair 198 199 for (Map.Entry<WritableComparable, Writable> e: instance.entrySet()) { 200 out.writeByte(getId(e.getKey().getClass())); 201 e.getKey().write(out); 202 out.writeByte(getId(e.getValue().getClass())); 203 e.getValue().write(out); 204 } 205 } 206 207 @Override 208 public boolean equals(Object obj) { 209 if (this == obj) { 210 return true; 211 } 212 213 if (obj instanceof SortedMapWritable) { 214 Map map = (Map) obj; 215 if (size() != map.size()) { 216 return false; 217 } 218 219 return entrySet().equals(map.entrySet()); 220 } 221 222 return false; 223 } 224 225 @Override 226 public int hashCode() { 227 return instance.hashCode(); 228 } 229}