1 19 package gnu.trove; 20 21 import java.io.IOException; 22 import java.io.ObjectInputStream; 23 import java.io.ObjectOutputStream; 24 import java.io.Serializable; 25 26 34 public class TByteObjectHashMap extends TByteHash implements Serializable { 35 36 37 static final long serialVersionUID = 1L; 38 39 40 protected transient Object[] _values; 41 42 46 public TByteObjectHashMap() { 47 super(); 48 } 49 50 57 public TByteObjectHashMap(int initialCapacity) { 58 super(initialCapacity); 59 } 60 61 69 public TByteObjectHashMap(int initialCapacity, float loadFactor) { 70 super(initialCapacity, loadFactor); 71 } 72 73 78 public TByteObjectHashMap(TByteHashingStrategy strategy) { 79 super(strategy); 80 } 81 82 90 public TByteObjectHashMap(int initialCapacity, TByteHashingStrategy strategy) { 91 super(initialCapacity, strategy); 92 } 93 94 103 public TByteObjectHashMap(int initialCapacity, float loadFactor, TByteHashingStrategy strategy) { 104 super(initialCapacity, loadFactor, strategy); 105 } 106 107 110 public Object clone() { 111 TByteObjectHashMap m = (TByteObjectHashMap)super.clone(); 112 m._values = (Object[])this._values.clone(); 113 return m; 114 } 115 116 119 public TByteObjectIterator iterator() { 120 return new TByteObjectIterator(this); 121 } 122 123 130 protected int setUp(int initialCapacity) { 131 int capacity; 132 133 capacity = super.setUp(initialCapacity); 134 _values = new Object[capacity]; 135 return capacity; 136 } 137 138 146 public Object put(byte key, Object value) { 147 byte previousState; 148 Object previous = null; 149 int index = insertionIndex(key); 150 boolean isNewMapping = true; 151 if (index < 0) { 152 index = -index -1; 153 previous = _values[index]; 154 isNewMapping = false; 155 } 156 previousState = _states[index]; 157 _set[index] = key; 158 _states[index] = FULL; 159 _values[index] = value; 160 if (isNewMapping) { 161 postInsertHook(previousState == FREE); 162 } 163 164 return previous; 165 } 166 167 172 protected void rehash(int newCapacity) { 173 int oldCapacity = _set.length; 174 byte oldKeys[] = _set; 175 Object oldVals[] = _values; 176 byte oldStates[] = _states; 177 178 _set = new byte[newCapacity]; 179 _values = new Object[newCapacity]; 180 _states = new byte[newCapacity]; 181 182 for (int i = oldCapacity; i-- > 0;) { 183 if(oldStates[i] == FULL) { 184 byte o = oldKeys[i]; 185 int index = insertionIndex(o); 186 _set[index] = o; 187 _values[index] = oldVals[i]; 188 _states[index] = FULL; 189 } 190 } 191 } 192 193 199 public Object get(byte key) { 200 int index = index(key); 201 return index < 0 ? null : _values[index]; 202 } 203 204 208 public void clear() { 209 super.clear(); 210 byte[] keys = _set; 211 Object[] vals = _values; 212 byte[] states = _states; 213 214 for (int i = keys.length; i-- > 0;) { 215 keys[i] = (byte)0; 216 vals[i] = null; 217 states[i] = FREE; 218 } 219 } 220 221 227 public Object remove(byte key) { 228 Object prev = null; 229 int index = index(key); 230 if (index >= 0) { 231 prev = _values[index]; 232 removeAt(index); } 234 return prev; 235 } 236 237 244 public boolean equals(Object other) { 245 if (! (other instanceof TByteObjectHashMap)) { 246 return false; 247 } 248 TByteObjectHashMap that = (TByteObjectHashMap)other; 249 if (that.size() != this.size()) { 250 return false; 251 } 252 return forEachEntry(new EqProcedure(that)); 253 } 254 255 public int hashCode() { 256 HashProcedure p = new HashProcedure(); 257 forEachEntry(p); 258 return p.getHashCode(); 259 } 260 261 private final class HashProcedure implements TByteObjectProcedure { 262 private int h = 0; 263 264 public int getHashCode() { 265 return h; 266 } 267 268 public final boolean execute(byte key, Object value) { 269 h += (_hashingStrategy.computeHashCode(key) ^ HashFunctions.hash(value)); 270 return true; 271 } 272 } 273 274 private static final class EqProcedure implements TByteObjectProcedure { 275 private final TByteObjectHashMap _otherMap; 276 277 EqProcedure(TByteObjectHashMap otherMap) { 278 _otherMap = otherMap; 279 } 280 281 public final boolean execute(byte key, Object value) { 282 int index = _otherMap.index(key); 283 if (index >= 0 && eq(value, _otherMap.get(key))) { 284 return true; 285 } 286 return false; 287 } 288 289 292 private final boolean eq(Object o1, Object o2) { 293 return o1 == o2 || ((o1 != null) && o1.equals(o2)); 294 } 295 296 } 297 298 303 protected void removeAt(int index) { 304 super.removeAt(index); _values[index] = null; 306 } 307 308 313 public Object[] getValues() { 314 Object[] vals = new Object[size()]; 315 Object[] v = _values; 316 byte[] states = _states; 317 318 for (int i = v.length, j = 0; i-- > 0;) { 319 if (states[i] == FULL) { 320 vals[j++] = v[i]; 321 } 322 } 323 return vals; 324 } 325 326 331 public byte[] keys() { 332 byte[] keys = new byte[size()]; 333 byte[] k = _set; 334 byte[] states = _states; 335 336 for (int i = k.length, j = 0; i-- > 0;) { 337 if (states[i] == FULL) { 338 keys[j++] = k[i]; 339 } 340 } 341 return keys; 342 } 343 344 350 public boolean containsValue(Object val) { 351 byte[] states = _states; 352 Object[] vals = _values; 353 354 if (null == val) { 357 for (int i = vals.length; i-- > 0;) { 358 if (states[i] == FULL && 359 val == vals[i]) { 360 return true; 361 } 362 } 363 } else { 364 for (int i = vals.length; i-- > 0;) { 365 if (states[i] == FULL && 366 (val == vals[i] || val.equals(vals[i]))) { 367 return true; 368 } 369 } 370 } return false; 372 } 373 374 375 381 public boolean containsKey(byte key) { 382 return contains(key); 383 } 384 385 392 public boolean forEachKey(TByteProcedure procedure) { 393 return forEach(procedure); 394 } 395 396 403 public boolean forEachValue(TObjectProcedure procedure) { 404 byte[] states = _states; 405 Object[] values = _values; 406 for (int i = values.length; i-- > 0;) { 407 if (states[i] == FULL && ! procedure.execute(values[i])) { 408 return false; 409 } 410 } 411 return true; 412 } 413 414 422 public boolean forEachEntry(TByteObjectProcedure procedure) { 423 byte[] states = _states; 424 byte[] keys = _set; 425 Object[] values = _values; 426 for (int i = keys.length; i-- > 0;) { 427 if (states[i] == FULL && ! procedure.execute(keys[i],values[i])) { 428 return false; 429 } 430 } 431 return true; 432 } 433 434 441 public boolean retainEntries(TByteObjectProcedure procedure) { 442 boolean modified = false; 443 byte[] states = _states; 444 byte[] keys = _set; 445 Object[] values = _values; 446 for (int i = keys.length; i-- > 0;) { 447 if (states[i] == FULL && ! procedure.execute(keys[i],values[i])) { 448 removeAt(i); 449 modified = true; 450 } 451 } 452 return modified; 453 } 454 455 460 public void transformValues(TObjectFunction function) { 461 byte[] states = _states; 462 Object[] values = _values; 463 for (int i = values.length; i-- > 0;) { 464 if (states[i] == FULL) { 465 values[i] = function.execute(values[i]); 466 } 467 } 468 } 469 470 471 472 private void writeObject(ObjectOutputStream stream) 473 throws IOException { 474 stream.defaultWriteObject(); 475 476 stream.writeInt(_size); 478 479 SerializationProcedure writeProcedure = new SerializationProcedure(stream); 480 if (! forEachEntry(writeProcedure)) { 481 throw writeProcedure.exception; 482 } 483 } 484 485 private void readObject(ObjectInputStream stream) 486 throws IOException, ClassNotFoundException { 487 stream.defaultReadObject(); 488 489 int size = stream.readInt(); 490 setUp(size); 491 while (size-- > 0) { 492 byte key = stream.readByte(); 493 Object val = stream.readObject(); 494 put(key, val); 495 } 496 } 497 } | Popular Tags |