scolebourne 2003/01/18 04:47:34
Modified: collections/src/java/org/apache/commons/collections
FastHashMap.java
Log:
Update licence
Javadoc improvements
Layout changes
Revision Changes Path
1.11 +246 -259
jakarta-commons/collections/src/java/org/apache/commons/collections/FastHashMap.java
Index: FastHashMap.java
===================================================================
RCS file:
/home/cvs/jakarta-commons/collections/src/java/org/apache/commons/collections/FastHashMap.java,v
retrieving revision 1.10
retrieving revision 1.11
diff -u -r1.10 -r1.11
--- FastHashMap.java 12 Oct 2002 22:15:18 -0000 1.10
+++ FastHashMap.java 18 Jan 2003 12:47:34 -0000 1.11
@@ -1,13 +1,10 @@
/*
* $Header$
- * $Revision$
- * $Date$
- *
* ====================================================================
*
* The Apache Software License, Version 1.1
*
- * Copyright (c) 1999-2002 The Apache Software Foundation. All rights
+ * Copyright (c) 1999-2003 The Apache Software Foundation. All rights
* reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -23,11 +20,11 @@
* distribution.
*
* 3. The end-user documentation included with the redistribution, if
- * any, must include the following acknowlegement:
+ * any, must include the following acknowledgment:
* "This product includes software developed by the
* Apache Software Foundation (http://www.apache.org/)."
- * Alternately, this acknowlegement may appear in the software itself,
- * if and wherever such third-party acknowlegements normally appear.
+ * Alternately, this acknowledgment may appear in the software itself,
+ * if and wherever such third-party acknowledgments normally appear.
*
* 4. The names "The Jakarta Project", "Commons", and "Apache Software
* Foundation" must not be used to endorse or promote products derived
@@ -36,7 +33,7 @@
*
* 5. Products derived from this software may not be called "Apache"
* nor may "Apache" appear in their names without prior written
- * permission of the Apache Group.
+ * permission of the Apache Software Foundation.
*
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
@@ -58,11 +55,8 @@
* <http://www.apache.org/>.
*
*/
-
-
package org.apache.commons.collections;
-
import java.util.Collection;
import java.util.ConcurrentModificationException;
import java.util.HashMap;
@@ -70,7 +64,6 @@
import java.util.Map;
import java.util.Set;
-
/**
* <p>A customized implementation of <code>java.util.HashMap</code> designed
* to operate in a multithreaded environment where the large majority of
@@ -105,84 +98,68 @@
* <A Href="http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html">
* Double-Checked Locking Idiom Is Broken Declartion</A>.</P>
*
- * @since 1.0
- * @author Craig R. McClanahan
+ * @since Commons Collections 1.0
* @version $Revision$ $Date$
+ *
+ * @author Craig R. McClanahan
*/
-
public class FastHashMap extends HashMap {
+ /**
+ * The underlying map we are managing.
+ */
+ protected HashMap map = null;
- // ----------------------------------------------------------- Constructors
+ /**
+ * Are we currently operating in "fast" mode?
+ */
+ protected boolean fast = false;
+ // Constructors
+ // ----------------------------------------------------------------------
/**
- * Construct a an empty map.
+ * Construct an empty map.
*/
public FastHashMap() {
-
super();
this.map = new HashMap();
-
}
-
/**
* Construct an empty map with the specified capacity.
*
- * @param capacity The initial capacity of the empty map
+ * @param capacity the initial capacity of the empty map
*/
public FastHashMap(int capacity) {
-
super();
this.map = new HashMap(capacity);
-
}
-
/**
* Construct an empty map with the specified capacity and load factor.
*
- * @param capacity The initial capacity of the empty map
- * @param factor The load factor of the new map
+ * @param capacity the initial capacity of the empty map
+ * @param factor the load factor of the new map
*/
public FastHashMap(int capacity, float factor) {
-
super();
this.map = new HashMap(capacity, factor);
-
}
-
/**
* Construct a new map with the same mappings as the specified map.
*
- * @param map The map whose mappings are to be copied
+ * @param map the map whose mappings are to be copied
*/
public FastHashMap(Map map) {
-
super();
this.map = new HashMap(map);
-
}
- // ----------------------------------------------------- Instance Variables
-
-
- /**
- * The underlying map we are managing.
- */
- protected HashMap map = null;
-
-
- // ------------------------------------------------------------- Properties
-
-
- /**
- * Are we operating in "fast" mode?
- */
- protected boolean fast = false;
+ // Property access
+ // ----------------------------------------------------------------------
/**
* Returns true if this map is operating in fast mode.
@@ -203,57 +180,68 @@
}
- // --------------------------------------------------------- Public Methods
-
+ // Map access
+ // ----------------------------------------------------------------------
+ // These methods can forward straight to the wrapped Map in 'fast' mode.
+ // (because they are query methods)
/**
- * Remove all mappings from this map.
+ * Return the value to which this map maps the specified key. Returns
+ * <code>null</code> if the map contains no mapping for this key, or if
+ * there is a mapping with a value of <code>null</code>. Use the
+ * <code>containsKey()</code> method to disambiguate these cases.
+ *
+ * @param key the key whose value is to be returned
+ * @return the value mapped to that key, or null
*/
- public void clear() {
-
+ public Object get(Object key) {
if (fast) {
- synchronized (this) {
- HashMap temp = (HashMap) map.clone();
- temp.clear();
- map = temp;
- }
+ return (map.get(key));
} else {
synchronized (map) {
- map.clear();
+ return (map.get(key));
}
}
-
}
-
/**
- * Return a shallow copy of this <code>FastHashMap</code> instance.
- * The keys and values themselves are not copied.
+ * Return the number of key-value mappings in this map.
+ *
+ * @return the current size of the map
*/
- public Object clone() {
-
- FastHashMap results = null;
+ public int size() {
if (fast) {
- results = new FastHashMap(map);
+ return (map.size());
} else {
synchronized (map) {
- results = new FastHashMap(map);
+ return (map.size());
}
}
- results.setFast(getFast());
- return (results);
-
}
+ /**
+ * Return <code>true</code> if this map contains no mappings.
+ *
+ * @return is the map currently empty
+ */
+ public boolean isEmpty() {
+ if (fast) {
+ return (map.isEmpty());
+ } else {
+ synchronized (map) {
+ return (map.isEmpty());
+ }
+ }
+ }
/**
* Return <code>true</code> if this map contains a mapping for the
* specified key.
*
- * @param key Key to be searched for
+ * @param key the key to be searched for
+ * @return true if the map contains the key
*/
public boolean containsKey(Object key) {
-
if (fast) {
return (map.containsKey(key));
} else {
@@ -261,18 +249,16 @@
return (map.containsKey(key));
}
}
-
}
-
/**
* Return <code>true</code> if this map contains one or more keys mapping
* to the specified value.
*
- * @param value Value to be searched for
+ * @param value the value to be searched for
+ * @return true if the map contains the value
*/
public boolean containsValue(Object value) {
-
if (fast) {
return (map.containsValue(value));
} else {
@@ -280,238 +266,229 @@
return (map.containsValue(value));
}
}
+ }
+
+ // Map modification
+ // ----------------------------------------------------------------------
+ // These methods perform special behaviour in 'fast' mode.
+ // The map is cloned, updated and then assigned back.
+ // See the comments at the top as to why this won't always work.
+ /**
+ * Associate the specified value with the specified key in this map.
+ * If the map previously contained a mapping for this key, the old
+ * value is replaced and returned.
+ *
+ * @param key the key with which the value is to be associated
+ * @param value the value to be associated with this key
+ * @return the value previously mapped to the key, or null
+ */
+ public Object put(Object key, Object value) {
+ if (fast) {
+ synchronized (this) {
+ HashMap temp = (HashMap) map.clone();
+ Object result = temp.put(key, value);
+ map = temp;
+ return (result);
+ }
+ } else {
+ synchronized (map) {
+ return (map.put(key, value));
+ }
+ }
}
+ /**
+ * Copy all of the mappings from the specified map to this one, replacing
+ * any mappings with the same keys.
+ *
+ * @param in the map whose mappings are to be copied
+ */
+ public void putAll(Map in) {
+ if (fast) {
+ synchronized (this) {
+ HashMap temp = (HashMap) map.clone();
+ temp.putAll(in);
+ map = temp;
+ }
+ } else {
+ synchronized (map) {
+ map.putAll(in);
+ }
+ }
+ }
/**
- * Return a collection view of the mappings contained in this map. Each
- * element in the returned collection is a <code>Map.Entry</code>.
+ * Remove any mapping for this key, and return any previously
+ * mapped value.
+ *
+ * @param key the key whose mapping is to be removed
+ * @return the value removed, or null
*/
- public Set entrySet() {
- return new EntrySet();
+ public Object remove(Object key) {
+ if (fast) {
+ synchronized (this) {
+ HashMap temp = (HashMap) map.clone();
+ Object result = temp.remove(key);
+ map = temp;
+ return (result);
+ }
+ } else {
+ synchronized (map) {
+ return (map.remove(key));
+ }
+ }
}
+ /**
+ * Remove all mappings from this map.
+ */
+ public void clear() {
+ if (fast) {
+ synchronized (this) {
+ HashMap temp = (HashMap) map.clone();
+ temp.clear();
+ map = temp;
+ }
+ } else {
+ synchronized (map) {
+ map.clear();
+ }
+ }
+ }
+ // Basic object methods
+ // ----------------------------------------------------------------------
+
/**
* Compare the specified object with this list for equality. This
* implementation uses exactly the code that is used to define the
* list equals function in the documentation for the
* <code>Map.equals</code> method.
*
- * @param o Object to be compared to this list
+ * @param o the object to be compared to this list
+ * @return true if the two maps are equal
*/
public boolean equals(Object o) {
-
// Simple tests that require no synchronization
- if (o == this)
+ if (o == this) {
return (true);
- else if (!(o instanceof Map))
+ } else if (!(o instanceof Map)) {
return (false);
+ }
Map mo = (Map) o;
// Compare the two maps for equality
if (fast) {
- if (mo.size() != map.size())
+ if (mo.size() != map.size()) {
return (false);
- java.util.Iterator i = map.entrySet().iterator();
+ }
+ Iterator i = map.entrySet().iterator();
while (i.hasNext()) {
Map.Entry e = (Map.Entry) i.next();
Object key = e.getKey();
Object value = e.getValue();
if (value == null) {
- if (!(mo.get(key) == null && mo.containsKey(key)))
+ if (!(mo.get(key) == null && mo.containsKey(key))) {
return (false);
+ }
} else {
- if (!value.equals(mo.get(key)))
+ if (!value.equals(mo.get(key))) {
return (false);
+ }
}
}
return (true);
+
} else {
synchronized (map) {
- if (mo.size() != map.size())
+ if (mo.size() != map.size()) {
return (false);
- java.util.Iterator i = map.entrySet().iterator();
+ }
+ Iterator i = map.entrySet().iterator();
while (i.hasNext()) {
Map.Entry e = (Map.Entry) i.next();
Object key = e.getKey();
Object value = e.getValue();
if (value == null) {
- if (!(mo.get(key) == null && mo.containsKey(key)))
+ if (!(mo.get(key) == null && mo.containsKey(key))) {
return (false);
+ }
} else {
- if (!value.equals(mo.get(key)))
+ if (!value.equals(mo.get(key))) {
return (false);
+ }
}
}
return (true);
}
}
-
}
-
- /**
- * Return the value to which this map maps the specified key. Returns
- * <code>null</code> if the map contains no mapping for this key, or if
- * there is a mapping with a value of <code>null</code>. Use the
- * <code>containsKey()</code> method to disambiguate these cases.
- *
- * @param key Key whose value is to be returned
- */
- public Object get(Object key) {
-
- if (fast) {
- return (map.get(key));
- } else {
- synchronized (map) {
- return (map.get(key));
- }
- }
-
- }
-
-
/**
* Return the hash code value for this map. This implementation uses
* exactly the code that is used to define the list hash function in the
* documentation for the <code>Map.hashCode</code> method.
+ *
+ * @return suitable integer hashcode
*/
public int hashCode() {
-
if (fast) {
int h = 0;
- java.util.Iterator i = map.entrySet().iterator();
- while (i.hasNext())
+ Iterator i = map.entrySet().iterator();
+ while (i.hasNext()) {
h += i.next().hashCode();
+ }
return (h);
} else {
synchronized (map) {
int h = 0;
- java.util.Iterator i = map.entrySet().iterator();
- while (i.hasNext())
+ Iterator i = map.entrySet().iterator();
+ while (i.hasNext()) {
h += i.next().hashCode();
+ }
return (h);
}
}
-
}
-
/**
- * Return <code>true</code> if this map contains no mappings.
- */
- public boolean isEmpty() {
-
- if (fast) {
- return (map.isEmpty());
- } else {
- synchronized (map) {
- return (map.isEmpty());
- }
- }
-
- }
-
-
- /**
- * Return a set view of the keys contained in this map.
- */
- public Set keySet() {
- return new KeySet();
- }
-
-
- /**
- * Associate the specified value with the specified key in this map.
- * If the map previously contained a mapping for this key, the old
- * value is replaced and returned.
- *
- * @param key The key with which the value is to be associated
- * @param value The value to be associated with this key
- */
- public Object put(Object key, Object value) {
-
- if (fast) {
- synchronized (this) {
- HashMap temp = (HashMap) map.clone();
- Object result = temp.put(key, value);
- map = temp;
- return (result);
- }
- } else {
- synchronized (map) {
- return (map.put(key, value));
- }
- }
-
- }
-
-
- /**
- * Copy all of the mappings from the specified map to this one, replacing
- * any mappings with the same keys.
- *
- * @param in Map whose mappings are to be copied
+ * Return a shallow copy of this <code>FastHashMap</code> instance.
+ * The keys and values themselves are not copied.
+ *
+ * @return a clone of this map
*/
- public void putAll(Map in) {
-
+ public Object clone() {
+ FastHashMap results = null;
if (fast) {
- synchronized (this) {
- HashMap temp = (HashMap) map.clone();
- temp.putAll(in);
- map = temp;
- }
+ results = new FastHashMap(map);
} else {
synchronized (map) {
- map.putAll(in);
+ results = new FastHashMap(map);
}
}
-
+ results.setFast(getFast());
+ return (results);
}
-
+ // Map views
+ // ----------------------------------------------------------------------
+
/**
- * Remove any mapping for this key, and return any previously
- * mapped value.
- *
- * @param key Key whose mapping is to be removed
+ * Return a collection view of the mappings contained in this map. Each
+ * element in the returned collection is a <code>Map.Entry</code>.
*/
- public Object remove(Object key) {
-
- if (fast) {
- synchronized (this) {
- HashMap temp = (HashMap) map.clone();
- Object result = temp.remove(key);
- map = temp;
- return (result);
- }
- } else {
- synchronized (map) {
- return (map.remove(key));
- }
- }
-
+ public Set entrySet() {
+ return new EntrySet();
}
-
/**
- * Return the number of key-value mappings in this map.
+ * Return a set view of the keys contained in this map.
*/
- public int size() {
-
- if (fast) {
- return (map.size());
- } else {
- synchronized (map) {
- return (map.size());
- }
- }
-
+ public Set keySet() {
+ return new KeySet();
}
-
/**
* Return a collection view of the values contained in this map.
*/
@@ -519,7 +496,12 @@
return new Values();
}
+ // Map view inner classes
+ // ----------------------------------------------------------------------
+ /**
+ * Abstract collection implementation shared by ketSet(), values() and
entrySet().
+ */
private abstract class CollectionView implements Collection {
public CollectionView() {
@@ -728,45 +710,50 @@
}
}
}
- }
-
-
- private class KeySet extends CollectionView implements Set {
-
- protected Collection get(Map map) {
- return map.keySet();
- }
-
- protected Object iteratorNext(Map.Entry entry) {
- return entry.getKey();
- }
-
- }
-
-
- private class Values extends CollectionView {
-
- protected Collection get(Map map) {
- return map.values();
- }
-
- protected Object iteratorNext(Map.Entry entry) {
- return entry.getValue();
- }
- }
-
-
- private class EntrySet extends CollectionView implements Set {
-
- protected Collection get(Map map) {
- return map.entrySet();
- }
-
-
- protected Object iteratorNext(Map.Entry entry) {
- return entry;
- }
+ }
- }
+ /**
+ * Set implementation over the keys of the FastHashMap
+ */
+ private class KeySet extends CollectionView implements Set {
+
+ protected Collection get(Map map) {
+ return map.keySet();
+ }
+
+ protected Object iteratorNext(Map.Entry entry) {
+ return entry.getKey();
+ }
+
+ }
+
+ /**
+ * Collection implementation over the values of the FastHashMap
+ */
+ private class Values extends CollectionView {
+
+ protected Collection get(Map map) {
+ return map.values();
+ }
+
+ protected Object iteratorNext(Map.Entry entry) {
+ return entry.getValue();
+ }
+ }
+
+ /**
+ * Set implementation over the entries of the FastHashMap
+ */
+ private class EntrySet extends CollectionView implements Set {
+
+ protected Collection get(Map map) {
+ return map.entrySet();
+ }
+
+ protected Object iteratorNext(Map.Entry entry) {
+ return entry;
+ }
+
+ }
}
--
To unsubscribe, e-mail: <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>