一、vector与ArrayList区别
-
1 package java.util; 2 publicclassVector
3 extendsAbstractList 4 implementsList ,RandomAccess,Cloneable, java.io.Serializable 5 { 6 protectedObject[] elementData; 7 protectedint elementCount; 8 protectedint capacityIncrement; 9 privatestaticfinallong serialVersionUID =-2767605614048989439L; 10 publicVector(int initialCapacity,int capacityIncrement){ 11 super(); 12 if(initialCapacity <0) 13 thrownewIllegalArgumentException("Illegal Capacity: "+ 14 initialCapacity); 15 this.elementData =newObject[initialCapacity]; 16 this.capacityIncrement = capacityIncrement; 17 } 18 publicVector(int initialCapacity){ 19 this(initialCapacity,0); 20 } 21 publicVector(){ 22 this(10); 23 } 24 publicVector(Collection c){ 25 elementData = c.toArray(); 26 elementCount = elementData.length; 27 // c.toArray might (incorrectly) not return Object[] (see 6260652) 28 if(elementData.getClass()!=Object[].class) 29 elementData =Arrays.copyOf(elementData, elementCount,Object[].class); 30 } 31 publicsynchronizedvoid copyInto(Object[] anArray){ 32 System.arraycopy(elementData,0, anArray,0, elementCount); 33 } 34 /** 35 * Trims the capacity of this vector to be the vector's current 36 * size. If the capacity of this vector is larger than its current 37 * size, then the capacity is changed to equal the size by replacing 38 * its internal data array, kept in the field { @code elementData}, 39 * with a smaller one. An application can use this operation to 40 * minimize the storage of a vector. 41 */ 42 publicsynchronizedvoid trimToSize(){ 43 modCount++; 44 int oldCapacity = elementData.length; 45 if(elementCount < oldCapacity){ 46 elementData =Arrays.copyOf(elementData, elementCount); 47 } 48 } 49 publicsynchronizedvoid ensureCapacity(int minCapacity){ 50 modCount++; 51 ensureCapacityHelper(minCapacity); 52 } 53 /** 54 * This implements the unsynchronized semantics of ensureCapacity. 55 * Synchronized methods in this class can internally call this 56 * method for ensuring capacity without incurring the cost of an 57 * extra synchronization. 58 * 59 * @see #ensureCapacity(int) 60 */ 61 privatevoid ensureCapacityHelper(int minCapacity){ 62 int oldCapacity = elementData.length; 63 if(minCapacity > oldCapacity){ 64 Object[] oldData = elementData; 65 int newCapacity =(capacityIncrement >0)? 66 (oldCapacity + capacityIncrement):(oldCapacity *2); 67 if(newCapacity < minCapacity){ 68 newCapacity = minCapacity; 69 } 70 elementData =Arrays.copyOf(elementData, newCapacity); 71 } 72 } 73 /** 74 * Sets the size of this vector. If the new size is greater than the 75 * current size, new { @code null} items are added to the end of 76 * the vector. If the new size is less than the current size, all 77 * components at index { @code newSize} and greater are discarded. 78 * 79 * @param newSize the new size of this vector 80 * @throws ArrayIndexOutOfBoundsException if the new size is negative 81 */ 82 publicsynchronizedvoid setSize(int newSize){ 83 modCount++; 84 if(newSize > elementCount){ 85 ensureCapacityHelper(newSize); 86 }else{ 87 for(int i = newSize ; i < elementCount ; i++){ 88 elementData[i]=null; 89 } 90 } 91 elementCount = newSize; 92 } 93 /** 94 * Returns the current capacity of this vector. 95 * 96 * @return the current capacity (the length of its internal 97 * data array, kept in the field { @code elementData} 98 * of this vector) 99 */100 publicsynchronizedint capacity(){101 return elementData.length;102 }103 /**104 * Returns the number of components in this vector.105 *106 * @return the number of components in this vector107 */108 publicsynchronizedint size(){109 return elementCount;110 }111 /**112 * Tests if this vector has no components.113 *114 * @return { @code true} if and only if this vector has115 * no components, that is, its size is zero;116 * { @code false} otherwise.117 */118 publicsynchronizedboolean isEmpty(){119 return elementCount ==0;120 }121 /**122 * Returns an enumeration of the components of this vector. The123 * returned { @code Enumeration} object will generate all items in124 * this vector. The first item generated is the item at index { @code 0},125 * then the item at index { @code 1}, and so on.126 *127 * @return an enumeration of the components of this vector128 * @see Iterator129 */130 publicEnumeration elements(){131 returnnewEnumeration (){132 int count =0;133 publicboolean hasMoreElements(){134 return count < elementCount;135 }136 public E nextElement(){137 synchronized(Vector.this){138 if(count < elementCount){139 return(E)elementData[count++];140 }141 }142 thrownewNoSuchElementException("Vector Enumeration");143 }144 };145 }146 /**147 * Returns { @code true} if this vector contains the specified element.148 * More formally, returns { @code true} if and only if this vector149 * contains at least one element { @code e} such that150 * (o==null ? e==null : o.equals(e)).151 *152 * @param o element whose presence in this vector is to be tested153 * @return { @code true} if this vector contains the specified element154 */155 publicboolean contains(Object o){156 return indexOf(o,0)>=0;157 }158 /**159 * Returns the index of the first occurrence of the specified element160 * in this vector, or -1 if this vector does not contain the element.161 * More formally, returns the lowest index { @code i} such that162 * (o==null ? get(i)==null : o.equals(get(i))),163 * or -1 if there is no such index.164 *165 * @param o element to search for166 * @return the index of the first occurrence of the specified element in167 * this vector, or -1 if this vector does not contain the element168 */169 publicint indexOf(Object o){170 return indexOf(o,0);171 }172 /**173 * Returns the index of the first occurrence of the specified element in174 * this vector, searching forwards from { @code index}, or returns -1 if175 * the element is not found.176 * More formally, returns the lowest index { @code i} such that177 * (i >= index && (o==null ? get(i)==null : o.equals(get(i)))),178 * or -1 if there is no such index.179 *180 * @param o element to search for181 * @param index index to start searching from182 * @return the index of the first occurrence of the element in183 * this vector at position { @code index} or later in the vector;184 * { @code -1} if the element is not found.185 * @throws IndexOutOfBoundsException if the specified index is negative186 * @see Object#equals(Object)187 */188 publicsynchronizedint indexOf(Object o,int index){189 if(o ==null){190 for(int i = index ; i < elementCount ; i++)191 if(elementData[i]==null)192 return i;193 }else{194 for(int i = index ; i < elementCount ; i++)195 if(o.equals(elementData[i]))196 return i;197 }198 return-1;199 }200 /**201 * Returns the index of the last occurrence of the specified element202 * in this vector, or -1 if this vector does not contain the element.203 * More formally, returns the highest index { @code i} such that204 * (o==null ? get(i)==null : o.equals(get(i))),205 * or -1 if there is no such index.206 *207 * @param o element to search for208 * @return the index of the last occurrence of the specified element in209 * this vector, or -1 if this vector does not contain the element210 */211 publicsynchronizedint lastIndexOf(Object o){212 return lastIndexOf(o, elementCount-1);213 }214 /**215 * Returns the index of the last occurrence of the specified element in216 * this vector, searching backwards from { @code index}, or returns -1 if217 * the element is not found.218 * More formally, returns the highest index { @code i} such that219 * (i <= index && (o==null ? get(i)==null : o.equals(get(i)))),220 * or -1 if there is no such index.221 *222 * @param o element to search for223 * @param index index to start searching backwards from224 * @return the index of the last occurrence of the element at position225 * less than or equal to { @code index} in this vector;226 * -1 if the element is not found.227 * @throws IndexOutOfBoundsException if the specified index is greater228 * than or equal to the current size of this vector229 */230 publicsynchronizedint lastIndexOf(Object o,int index){231 if(index >= elementCount)232 thrownewIndexOutOfBoundsException(index +" >= "+ elementCount);233 if(o ==null){234 for(int i = index; i >=0; i--)235 if(elementData[i]==null)236 return i;237 }else{238 for(int i = index; i >=0; i--)239 if(o.equals(elementData[i]))240 return i;241 }242 return-1;243 }244 /**245 * Returns the component at the specified index.246 *247 * This method is identical in functionality to the { @link #get(int)}248 * method (which is part of the { @link List} interface).249 *250 * @param index an index into this vector251 * @return the component at the specified index252 * @throws ArrayIndexOutOfBoundsException if the index is out of range253 * ({ @code index < 0 || index >= size()})254 */255 publicsynchronized E elementAt(int index){256 if(index >= elementCount){257 thrownewArrayIndexOutOfBoundsException(index +" >= "+ elementCount);258 }259 return(E)elementData[index];260 }261 /**262 * Returns the first component (the item at index { @code 0}) of263 * this vector.264 *265 * @return the first component of this vector266 * @throws NoSuchElementException if this vector has no components267 */268 publicsynchronized E firstElement(){269 if(elementCount ==0){270 thrownewNoSuchElementException();271 }272 return(E)elementData[0];273 }274 /**275 * Returns the last component of the vector.276 *277 * @return the last component of the vector, i.e., the component at index278 *
size() - 1
.279 * @throws NoSuchElementException if this vector is empty280 */281 publicsynchronized E lastElement(){282 if(elementCount ==0){283 thrownewNoSuchElementException();284 }285 return(E)elementData[elementCount -1];286 }287 /**288 * Sets the component at the specified { @code index} of this289 * vector to be the specified object. The previous component at that290 * position is discarded.291 *292 *The index must be a value greater than or equal to { @code 0}293 * and less than the current size of the vector.294 *295 *
This method is identical in functionality to the296 * { @link #set(int, Object) set(int, E)}297 * method (which is part of the { @link List} interface). Note that the298 * { @code set} method reverses the order of the parameters, to more closely299 * match array usage. Note also that the { @code set} method returns the300 * old value that was stored at the specified position.301 *302 * @param obj what the component is to be set to303 * @param index the specified index304 * @throws ArrayIndexOutOfBoundsException if the index is out of range305 * ({ @code index < 0 || index >= size()})306 */307 publicsynchronizedvoid setElementAt(E obj,int index){308 if(index >= elementCount){309 thrownewArrayIndexOutOfBoundsException(index +" >= "+310 elementCount);311 }312 elementData[index]= obj;313 }314 publicsynchronizedvoid removeElementAt(int index){315 modCount++;316 if(index >= elementCount){317 thrownewArrayIndexOutOfBoundsException(index +" >= "+318 elementCount);319 }320 elseif(index <0){321 thrownewArrayIndexOutOfBoundsException(index);322 }323 int j = elementCount - index -1;324 if(j >0){325 System.arraycopy(elementData, index +1, elementData, index, j);326 }327 elementCount--;328 elementData[elementCount]=null;/* to let gc do its work */329 }330 /**331 * Inserts the specified object as a component in this vector at the332 * specified { @code index}. Each component in this vector with333 * an index greater or equal to the specified { @code index} is334 * shifted upward to have an index one greater than the value it had335 * previously.336 *337 *
The index must be a value greater than or equal to { @code 0}338 * and less than or equal to the current size of the vector. (If the339 * index is equal to the current size of the vector, the new element340 * is appended to the Vector.)341 *342 *
This method is identical in functionality to the343 * { @link #add(int, Object) add(int, E)}344 * method (which is part of the { @link List} interface). Note that the345 * { @code add} method reverses the order of the parameters, to more closely346 * match array usage.347 *348 * @param obj the component to insert349 * @param index where to insert the new component350 * @throws ArrayIndexOutOfBoundsException if the index is out of range351 * ({ @code index < 0 || index > size()})352 */353 publicsynchronizedvoid insertElementAt(E obj,int index){354 modCount++;355 if(index > elementCount){356 thrownewArrayIndexOutOfBoundsException(index357 +" > "+ elementCount);358 }359 ensureCapacityHelper(elementCount +1);360 System.arraycopy(elementData, index, elementData, index +1, elementCount - index);361 elementData[index]= obj;362 elementCount++;363 }364 /**365 * Adds the specified component to the end of this vector,366 * increasing its size by one. The capacity of this vector is367 * increased if its size becomes greater than its capacity.368 *369 *
This method is identical in functionality to the370 * { @link #add(Object) add(E)}371 * method (which is part of the { @link List} interface).372 *373 * @param obj the component to be added374 */375 publicsynchronizedvoid addElement(E obj){376 modCount++;377 ensureCapacityHelper(elementCount +1);378 elementData[elementCount++]= obj;379 }380 /**381 * Removes the first (lowest-indexed) occurrence of the argument382 * from this vector. If the object is found in this vector, each383 * component in the vector with an index greater or equal to the384 * object's index is shifted downward to have an index one smaller385 * than the value it had previously.386 *387 *
This method is identical in functionality to the388 * { @link #remove(Object)} method (which is part of the389 * { @link List} interface).390 *391 * @param obj the component to be removed392 * @return { @code true} if the argument was a component of this393 * vector; { @code false} otherwise.394 */395 publicsynchronizedboolean removeElement(Object obj){396 modCount++;397 int i = indexOf(obj);398 if(i >=0){399 removeElementAt(i);400 returntrue;401 }402 returnfalse;403 }404 /**405 * Removes all components from this vector and sets its size to zero.406 *407 *
This method is identical in functionality to the { @link #clear}408 * method (which is part of the { @link List} interface).409 */410 publicsynchronizedvoid removeAllElements(){411 modCount++;412 // Let gc do its work413 for(int i =0; i < elementCount; i++)414 elementData[i]=null;415 elementCount =0;416 }417 /**418 * Returns a clone of this vector. The copy will contain a419 * reference to a clone of the internal data array, not a reference420 * to the original internal data array of this { @code Vector} object.421 *422 * @return a clone of this vector423 */424 publicsynchronizedObject clone(){425 try{426 Vector
v =(Vector )super.clone();427 v.elementData =Arrays.copyOf(elementData, elementCount);428 v.modCount =0;429 return v;430 }catch(CloneNotSupportedException e){431 // this shouldn't happen, since we are Cloneable432 thrownewInternalError();433 }434 }435 /**436 * Returns an array containing all of the elements in this Vector437 * in the correct order.438 *439 * @since 1.2440 */441 publicsynchronizedObject[] toArray(){442 returnArrays.copyOf(elementData, elementCount);443 }444 publicsynchronized T[] toArray(T[] a){445 if(a.length < elementCount)446 return(T[])Arrays.copyOf(elementData, elementCount, a.getClass());447 System.arraycopy(elementData,0, a,0, elementCount);448 if(a.length > elementCount)449 a[elementCount]=null;450 return a;451 }452 // Positional Access Operations453 /**454 * Returns the element at the specified position in this Vector.455 *456 * @param index index of the element to return457 * @return object at the specified index458 * @throws ArrayIndexOutOfBoundsException if the index is out of range459 * ({ @code index < 0 || index >= size()})460 * @since 1.2461 */462 publicsynchronized E get(int index){463 if(index >= elementCount)464 thrownewArrayIndexOutOfBoundsException(index);465 return(E)elementData[index];466 }467 /**468 * Replaces the element at the specified position in this Vector with the469 * specified element.470 *471 * @param index index of the element to replace472 * @param element element to be stored at the specified position473 * @return the element previously at the specified position474 * @throws ArrayIndexOutOfBoundsException if the index is out of range475 * ({ @code index < 0 || index >= size()})476 * @since 1.2477 */478 publicsynchronized E set(int index, E element){479 if(index >= elementCount)480 thrownewArrayIndexOutOfBoundsException(index);481 Object oldValue = elementData[index];482 elementData[index]= element;483 return(E)oldValue;484 }485 /**486 * Appends the specified element to the end of this Vector.487 *488 * @param e element to be appended to this Vector489 * @return { @code true} (as specified by { @link Collection#add})490 * @since 1.2491 */492 publicsynchronizedboolean add(E e){493 modCount++;494 ensureCapacityHelper(elementCount +1);495 elementData[elementCount++]= e;496 returntrue;497 }498 publicboolean remove(Object o){499 return removeElement(o);500 }501 publicvoid add(int index, E element){502 insertElementAt(element, index);503 }504 publicsynchronized E remove(int index){505 modCount++;506 if(index >= elementCount)507 thrownewArrayIndexOutOfBoundsException(index);508 Object oldValue = elementData[index];509 int numMoved = elementCount - index -1;510 if(numMoved >0)511 System.arraycopy(elementData, index+1, elementData, index,512 numMoved);513 elementData[--elementCount]=null;// Let gc do its work514 return(E)oldValue;515 }516 publicvoid clear(){517 removeAllElements();518 }519 // Bulk Operations520 publicsynchronizedboolean containsAll(Collection c){521 returnsuper.containsAll(c);522 }523 publicsynchronizedboolean addAll(Collection c){524 modCount++;525 Object[] a = c.toArray();526 int numNew = a.length;527 ensureCapacityHelper(elementCount + numNew);528 System.arraycopy(a,0, elementData, elementCount, numNew);529 elementCount += numNew;530 return numNew !=0;531 }532 publicsynchronizedboolean removeAll(Collection c){533 returnsuper.removeAll(c);534 }535 publicsynchronizedboolean retainAll(Collection c){536 returnsuper.retainAll(c);537 }538 publicsynchronizedboolean addAll(int index,Collection c){539 modCount++;540 if(index <0|| index > elementCount)541 thrownewArrayIndexOutOfBoundsException(index);542 Object[] a = c.toArray();543 int numNew = a.length;544 ensureCapacityHelper(elementCount + numNew);545 int numMoved = elementCount - index;546 if(numMoved >0)547 System.arraycopy(elementData, index, elementData, index + numNew,548 numMoved);549 System.arraycopy(a,0, elementData, index, numNew);550 elementCount += numNew;551 return numNew !=0;552 }553 /**554 * Compares the specified Object with this Vector for equality. Returns555 * true if and only if the specified Object is also a List, both Lists556 * have the same size, and all corresponding pairs of elements in the two557 * Lists are equal. (Two elements { @code e1} and558 * { @code e2} are equal if { @code (e1==null ? e2==null :559 * e1.equals(e2))}.) In other words, two Lists are defined to be560 * equal if they contain the same elements in the same order.561 *562 * @param o the Object to be compared for equality with this Vector563 * @return true if the specified Object is equal to this Vector564 */565 publicsynchronizedboolean equals(Object o){566 returnsuper.equals(o);567 }568 /**569 * Returns the hash code value for this Vector.570 */571 publicsynchronizedint hashCode(){572 returnsuper.hashCode();573 }574 /**575 * Returns a string representation of this Vector, containing576 * the String representation of each element.577 */578 publicsynchronizedString toString(){579 returnsuper.toString();580 }581 publicsynchronizedList subList(int fromIndex,int toIndex){582 returnCollections.synchronizedList(super.subList(fromIndex, toIndex),583 this);584 }585 protectedsynchronizedvoid removeRange(int fromIndex,int toIndex){586 modCount++;587 int numMoved = elementCount - toIndex;588 System.arraycopy(elementData, toIndex, elementData, fromIndex,589 numMoved);590 // Let gc do its work591 int newElementCount = elementCount -(toIndex-fromIndex);592 while(elementCount != newElementCount)593 elementData[--elementCount]=null;594 }595 privatesynchronizedvoid writeObject(java.io.ObjectOutputStream s)596 throws java.io.IOException597 {598 s.defaultWriteObject();599 }600 }
1 package java.util; 2 import java.io.*; 3 publicclassHashMap4 extendsAbstractMap 5 implementsMap ,Cloneable,Serializable 6 { 7 /** 8 * The default initial capacity - MUST be a power of two. 9 */ 10 staticfinalint DEFAULT_INITIAL_CAPACITY =16; 11 /** 12 * The maximum capacity, used if a higher value is implicitly specified 13 * by either of the constructors with arguments. 14 * MUST be a power of two <= 1<<30. 15 */ 16 staticfinalint MAXIMUM_CAPACITY =1<<30; 17 /** 18 * The load factor used when none specified in constructor. 19 */ 20 staticfinalfloat DEFAULT_LOAD_FACTOR =0.75f; 21 /** 22 * The table, resized as necessary. Length MUST Always be a power of two. 23 */ 24 transientEntry[] table; 25 /** 26 * The number of key-value mappings contained in this map. 27 */ 28 transientint size; 29 /** 30 * The next size value at which to resize (capacity * load factor). 31 * @serial 32 */ 33 int threshold; 34 /** 35 * The load factor for the hash table. 36 * 37 * @serial 38 */ 39 finalfloat loadFactor; 40 /** 41 * The number of times this HashMap has been structurally modified 42 * Structural modifications are those that change the number of mappings in 43 * the HashMap or otherwise modify its internal structure (e.g., 44 * rehash). This field is used to make iterators on Collection-views of 45 * the HashMap fail-fast. (See ConcurrentModificationException). 46 */ 47 transientvolatileint modCount; 48 /** 49 * Constructs an empty HashMap with the specified initial 50 * capacity and load factor. 51 * 52 * @param initialCapacity the initial capacity 53 * @param loadFactor the load factor 54 * @throws IllegalArgumentException if the initial capacity is negative 55 * or the load factor is nonpositive 56 */ 57 publicHashMap(int initialCapacity,float loadFactor){ 58 if(initialCapacity <0) 59 thrownewIllegalArgumentException("Illegal initial capacity: "+ 60 initialCapacity); 61 if(initialCapacity > MAXIMUM_CAPACITY) 62 initialCapacity = MAXIMUM_CAPACITY; 63 if(loadFactor <=0||Float.isNaN(loadFactor)) 64 thrownewIllegalArgumentException("Illegal load factor: "+ 65 loadFactor); 66 // Find a power of 2 >= initialCapacity 67 int capacity =1; 68 while(capacity < initialCapacity) 69 capacity <<=1; 70 this.loadFactor = loadFactor; 71 threshold =(int)(capacity * loadFactor); 72 table =newEntry[capacity]; 73 init(); 74 } 75 /** 76 * Constructs an empty HashMap with the specified initial 77 * capacity and the default load factor (0.75). 78 * 79 * @param initialCapacity the initial capacity. 80 * @throws IllegalArgumentException if the initial capacity is negative. 81 */ 82 publicHashMap(int initialCapacity){ 83 this(initialCapacity, DEFAULT_LOAD_FACTOR); 84 } 85 /** 86 * Constructs an empty HashMap with the default initial capacity 87 * (16) and the default load factor (0.75). 88 */ 89 publicHashMap(){ 90 this.loadFactor = DEFAULT_LOAD_FACTOR; 91 threshold =(int)(DEFAULT_INITIAL_CAPACITY * DEFAULT_LOAD_FACTOR); 92 table =newEntry[DEFAULT_INITIAL_CAPACITY]; 93 init(); 94 } 95 /** 96 * Constructs a new HashMap with the same mappings as the 97 * specified Map. The HashMap is created with 98 * default load factor (0.75) and an initial capacity sufficient to 99 * hold the mappings in the specified Map.100 *101 * @param m the map whose mappings are to be placed in this map102 * @throws NullPointerException if the specified map is null103 */104 publicHashMap(Map m){105 this(Math.max((int)(m.size()/ DEFAULT_LOAD_FACTOR)+1,106 DEFAULT_INITIAL_CAPACITY), DEFAULT_LOAD_FACTOR);107 putAllForCreate(m);108 }109 // internal utilities110 /**111 * Initialization hook for subclasses. This method is called112 * in all constructors and pseudo-constructors (clone, readObject)113 * after HashMap has been initialized but before any entries have114 * been inserted. (In the absence of this method, readObject would115 * require explicit knowledge of subclasses.)116 */117 void init(){118 }119 /**120 * Applies a supplemental hash function to a given hashCode, which121 * defends against poor quality hash functions. This is critical122 * because HashMap uses power-of-two length hash tables, that123 * otherwise encounter collisions for hashCodes that do not differ124 * in lower bits. Note: Null keys always map to hash 0, thus index 0.125 */126 staticint hash(int h){127 // This function ensures that hashCodes that differ only by128 // constant multiples at each bit position have a bounded129 // number of collisions (approximately 8 at default load factor).130 h ^=(h >>>20)^(h >>>12);131 return h ^(h >>>7)^(h >>>4);132 }133 /**134 * Returns index for hash code h.135 */136 staticint indexFor(int h,int length){137 return h &(length-1);138 }139 /**140 * Returns the number of key-value mappings in this map.141 *142 * @return the number of key-value mappings in this map143 */144 publicint size(){145 return size;146 }147 /**148 * Returns true if this map contains no key-value mappings.149 *150 * @return true if this map contains no key-value mappings151 */152 publicboolean isEmpty(){153 return size ==0;154 }155 /**156 * Returns the value to which the specified key is mapped,157 * or { @code null} if this map contains no mapping for the key.158 *159 * More formally, if this map contains a mapping from a key160 * {
@code k} to a value { @code v} such that { @code (key==null ? k==null :161 * key.equals(k))}, then this method returns { @code v}; otherwise162 * it returns { @code null}. (There can be at most one such mapping.)163 *164 *A return value of {
@code null} does not necessarily165 * indicate that the map contains no mapping for the key; it's also166 * possible that the map explicitly maps the key to { @code null}.167 * The { @link #containsKey containsKey} operation may be used to168 * distinguish these two cases.169 *170 * @see #put(Object, Object)171 */172 public V get(Object key){173 if(key ==null)174 return getForNullKey();175 int hash = hash(key.hashCode());176 for(Entrye = table[indexFor(hash, table.length)];177 e !=null;178 e = e.next){179 Object k;180 if(e.hash == hash &&((k = e.key)== key || key.equals(k)))181 return e.value;182 }183 returnnull;184 }185 /**186 * Offloaded version of get() to look up null keys. Null keys map187 * to index 0. This null case is split out into separate methods188 * for the sake of performance in the two most commonly used189 * operations (get and put), but incorporated with conditionals in190 * others.191 */192 private V getForNullKey(){193 for(Entry e = table[0]; e !=null; e = e.next){194 if(e.key ==null)195 return e.value;196 }197 returnnull;198 }199 /**200 * Returns true if this map contains a mapping for the201 * specified key.202 *203 * @param key The key whose presence in this map is to be tested204 * @return true if this map contains a mapping for the specified205 * key.206 */207 publicboolean containsKey(Object key){208 return getEntry(key)!=null;209 }210 /**211 * Returns the entry associated with the specified key in the212 * HashMap. Returns null if the HashMap contains no mapping213 * for the key.214 */215 finalEntry getEntry(Object key){216 int hash =(key ==null)?0: hash(key.hashCode());217 for(Entry e = table[indexFor(hash, table.length)];218 e !=null;219 e = e.next){220 Object k;221 if(e.hash == hash &&222 ((k = e.key)== key ||(key !=null&& key.equals(k))))223 return e;224 }225 returnnull;226 }227 /**228 * Associates the specified value with the specified key in this map.229 * If the map previously contained a mapping for the key, the old230 * value is replaced.231 *232 * @param key key with which the specified value is to be associated233 * @param value value to be associated with the specified key234 * @return the previous value associated with key, or235 * null if there was no mapping for key.236 * (A null return can also indicate that the map237 * previously associated null with key.)238 */239 public V put(K key, V value){240 if(key ==null)241 return putForNullKey(value);242 int hash = hash(key.hashCode());243 int i = indexFor(hash, table.length);244 for(Entry e = table[i]; e !=null; e = e.next){245 Object k;246 if(e.hash == hash &&((k = e.key)== key || key.equals(k))){247 V oldValue = e.value;248 e.value = value;249 e.recordAccess(this);250 return oldValue;251 }252 }253 modCount++;254 addEntry(hash, key, value, i);255 returnnull;256 }257 /**258 * Offloaded version of put for null keys259 */260 private V putForNullKey(V value){261 for(Entry e = table[0]; e !=null; e = e.next){262 if(e.key ==null){263 V oldValue = e.value;264 e.value = value;265 e.recordAccess(this);266 return oldValue;267 }268 }269 modCount++;270 addEntry(0,null, value,0);271 returnnull;272 }273 // These methods are used when serializing HashSets274 int capacity(){ return table.length;}275 float loadFactor(){ return loadFactor;}276 }277 278 HashTable类279 280 publicclassHashtable 281 extendsDictionary 282 implementsMap ,Cloneable, java.io.Serializable{283 /**284 * The hash table data.285 */286 privatetransientEntry[] table;287 /**288 * The total number of entries in the hash table.289 */290 privatetransientint count;291 /**292 * The table is rehashed when its size exceeds this threshold. (The293 * value of this field is (int)(capacity * loadFactor).)294 *295 * @serial296 */297 privateint threshold;298 /**299 * The load factor for the hashtable.300 *301 * @serial302 */303 privatefloat loadFactor;304 /**305 * The number of times this Hashtable has been structurally modified306 * Structural modifications are those that change the number of entries in307 * the Hashtable or otherwise modify its internal structure (e.g.,308 * rehash). This field is used to make iterators on Collection-views of309 * the Hashtable fail-fast. (See ConcurrentModificationException).310 */311 privatetransientint modCount =0;312 /** use serialVersionUID from JDK 1.0.2 for interoperability */313 privatestaticfinallong serialVersionUID =1421746759512286392L;314 /**315 * Constructs a new, empty hashtable with the specified initial316 * capacity and the specified load factor.317 *318 * @param initialCapacity the initial capacity of the hashtable.319 * @param loadFactor the load factor of the hashtable.320 * @exception IllegalArgumentException if the initial capacity is less321 * than zero, or if the load factor is nonpositive.322 */323 publicHashtable(int initialCapacity,float loadFactor){324 if(initialCapacity <0)325 thrownewIllegalArgumentException("Illegal Capacity: "+326 initialCapacity);327 if(loadFactor <=0||Float.isNaN(loadFactor))328 thrownewIllegalArgumentException("Illegal Load: "+loadFactor);329 if(initialCapacity==0)330 initialCapacity =1;331 this.loadFactor = loadFactor;332 table =newEntry[initialCapacity];333 threshold =(int)(initialCapacity * loadFactor);334 }335 /**336 * Constructs a new, empty hashtable with the specified initial capacity337 * and default load factor (0.75).338 *339 * @param initialCapacity the initial capacity of the hashtable.340 * @exception IllegalArgumentException if the initial capacity is less341 * than zero.342 */343 publicHashtable(int initialCapacity){344 this(initialCapacity,0.75f);345 }346 /**347 * Constructs a new, empty hashtable with a default initial capacity (11)348 * and load factor (0.75).349 */350 publicHashtable(){351 this(11,0.75f);352 }353 /**354 * Constructs a new hashtable with the same mappings as the given355 * Map. The hashtable is created with an initial capacity sufficient to356 * hold the mappings in the given Map and a default load factor (0.75).357 *358 * @param t the map whose mappings are to be placed in this map.359 * @throws NullPointerException if the specified map is null.360 * @since 1.2361 */362 publicHashtable(Map t){363 this(Math.max(2*t.size(),11),0.75f);364 putAll(t);365 }366 /**367 * Returns the number of keys in this hashtable.368 *369 * @return the number of keys in this hashtable.370 */371 publicsynchronizedint size(){372 return count;373 }374 /**375 * Tests if this hashtable maps no keys to values.376 *377 * @return true
if this hashtable maps no keys to values;378 *false
otherwise.379 */380 publicsynchronizedboolean isEmpty(){381 return count ==0;382 }383 /**384 * Returns an enumeration of the keys in this hashtable.385 *386 * @return an enumeration of the keys in this hashtable.387 * @see Enumeration388 * @see #elements()389 * @see #keySet()390 * @see Map391 */392 publicsynchronizedEnumerationkeys(){393 returnthis. getEnumeration(KEYS);394 }
- HashTable的方法是同步的,HashMap不能同步,所以在线程多的场合要使用HashTable;
- HashTable不允许空值(key和value都不可以为null),hashmap则可以为null
- HashTable有一个contains()的方法,功能和containsValue()一样
- HashTable使用Enumeration,而HashMap使用Iterator
- HashTabe中的hash数组默认大小为11,增长方式为old*2+1,hashmap的hash为16,是2的指数倍
- 哈希值的使用不同,HashTable直接使用对象hashcode,而HashMap会重新计算hash值