concurrenthashmap.java
来自「SRI international 发布的OAA框架软件」· Java 代码 · 共 1,427 行 · 第 1/4 页
JAVA
1,427 行
/**
* Returns an enumeration of the values in this table.
*
* @return an enumeration of the values in this table.
* @see #values
*/
public Enumeration elements() {
return new ValueIterator();
}
/* ---------------- Iterator Support -------------- */
abstract class HashIterator {
int nextSegmentIndex;
int nextTableIndex;
HashEntry[] currentTable;
HashEntry nextEntry;
HashEntry lastReturned;
HashIterator() {
nextSegmentIndex = segments.length - 1;
nextTableIndex = -1;
advance();
}
public boolean hasMoreElements() { return hasNext(); }
final void advance() {
if (nextEntry != null && (nextEntry = nextEntry.next) != null)
return;
while (nextTableIndex >= 0) {
if ( (nextEntry = (HashEntry)currentTable[nextTableIndex--]) != null)
return;
}
while (nextSegmentIndex >= 0) {
Segment seg = (Segment)segments[nextSegmentIndex--];
if (seg.count != 0) {
currentTable = seg.table;
for (int j = currentTable.length - 1; j >= 0; --j) {
if ( (nextEntry = (HashEntry)currentTable[j]) != null) {
nextTableIndex = j - 1;
return;
}
}
}
}
}
public boolean hasNext() { return nextEntry != null; }
HashEntry nextEntry() {
if (nextEntry == null)
throw new NoSuchElementException();
lastReturned = nextEntry;
advance();
return lastReturned;
}
public void remove() {
if (lastReturned == null)
throw new IllegalStateException();
ConcurrentHashMap.this.remove(lastReturned.key);
lastReturned = null;
}
}
final class KeyIterator extends HashIterator implements Iterator, Enumeration {
public Object next() { return super.nextEntry().key; }
public Object nextElement() { return super.nextEntry().key; }
}
final class ValueIterator extends HashIterator implements Iterator, Enumeration {
public Object next() { return super.nextEntry().value; }
public Object nextElement() { return super.nextEntry().value; }
}
/**
* Entry iterator. Exported Entry objects must write-through
* changes in setValue, even if the nodes have been cloned. So we
* cannot return internal HashEntry objects. Instead, the iterator
* itself acts as a forwarding pseudo-entry.
*/
final class EntryIterator extends HashIterator implements Map.Entry, Iterator {
public Object next() {
nextEntry();
return this;
}
public Object getKey() {
if (lastReturned == null)
throw new IllegalStateException("Entry was removed");
return lastReturned.key;
}
public Object getValue() {
if (lastReturned == null)
throw new IllegalStateException("Entry was removed");
return ConcurrentHashMap.this.get(lastReturned.key);
}
public Object setValue(Object value) {
if (lastReturned == null)
throw new IllegalStateException("Entry was removed");
return ConcurrentHashMap.this.put(lastReturned.key, value);
}
public boolean equals(Object o) {
// If not acting as entry, just use default.
if (lastReturned == null)
return super.equals(o);
if (!(o instanceof Map.Entry))
return false;
Map.Entry e = (Map.Entry)o;
return eq(getKey(), e.getKey()) && eq(getValue(), e.getValue());
}
public int hashCode() {
// If not acting as entry, just use default.
if (lastReturned == null)
return super.hashCode();
Object k = getKey();
Object v = getValue();
return ((k == null) ? 0 : k.hashCode()) ^
((v == null) ? 0 : v.hashCode());
}
public String toString() {
// If not acting as entry, just use default.
if (lastReturned == null)
return super.toString();
else
return getKey() + "=" + getValue();
}
boolean eq(Object o1, Object o2) {
return (o1 == null ? o2 == null : o1.equals(o2));
}
}
final class KeySet extends AbstractSet {
public Iterator iterator() {
return new KeyIterator();
}
public int size() {
return ConcurrentHashMap.this.size();
}
public boolean contains(Object o) {
return ConcurrentHashMap.this.containsKey(o);
}
public boolean remove(Object o) {
return ConcurrentHashMap.this.remove(o) != null;
}
public void clear() {
ConcurrentHashMap.this.clear();
}
public Object[] toArray() {
Collection c = new ArrayList();
for (Iterator i = iterator(); i.hasNext(); )
c.add(i.next());
return c.toArray();
}
public Object[] toArray(Object[] a) {
Collection c = new ArrayList();
for (Iterator i = iterator(); i.hasNext(); )
c.add(i.next());
return c.toArray(a);
}
}
final class Values extends AbstractCollection {
public Iterator iterator() {
return new ValueIterator();
}
public int size() {
return ConcurrentHashMap.this.size();
}
public boolean contains(Object o) {
return ConcurrentHashMap.this.containsValue(o);
}
public void clear() {
ConcurrentHashMap.this.clear();
}
public Object[] toArray() {
Collection c = new ArrayList();
for (Iterator i = iterator(); i.hasNext(); )
c.add(i.next());
return c.toArray();
}
public Object[] toArray(Object[] a) {
Collection c = new ArrayList();
for (Iterator i = iterator(); i.hasNext(); )
c.add(i.next());
return c.toArray(a);
}
}
final class EntrySet extends AbstractSet {
public Iterator iterator() {
return new EntryIterator();
}
public boolean contains(Object o) {
if (!(o instanceof Map.Entry))
return false;
Map.Entry e = (Map.Entry)o;
Object v = ConcurrentHashMap.this.get(e.getKey());
return v != null && v.equals(e.getValue());
}
public boolean remove(Object o) {
if (!(o instanceof Map.Entry))
return false;
Map.Entry e = (Map.Entry)o;
return ConcurrentHashMap.this.remove(e.getKey(), e.getValue());
}
public int size() {
return ConcurrentHashMap.this.size();
}
public void clear() {
ConcurrentHashMap.this.clear();
}
public Object[] toArray() {
// Since we don't ordinarily have distinct Entry objects, we
// must pack elements using exportable SimpleEntry
Collection c = new ArrayList(size());
for (Iterator i = iterator(); i.hasNext(); )
c.add(new SimpleEntry((Entry)i.next()));
return c.toArray();
}
public Object[] toArray(Object[] a) {
Collection c = new ArrayList(size());
for (Iterator i = iterator(); i.hasNext(); )
c.add(new SimpleEntry((Entry)i.next()));
return c.toArray(a);
}
}
/**
* This duplicates java.util.AbstractMap.SimpleEntry until this class
* is made accessible.
*/
static final class SimpleEntry implements Entry {
Object key;
Object value;
public SimpleEntry(Object key, Object value) {
this.key = key;
this.value = value;
}
public SimpleEntry(Entry e) {
this.key = e.getKey();
this.value = e.getValue();
}
public Object getKey() {
return key;
}
public Object getValue() {
return value;
}
public Object setValue(Object value) {
Object oldValue = this.value;
this.value = value;
return oldValue;
}
public boolean equals(Object o) {
if (!(o instanceof Map.Entry))
return false;
Map.Entry e = (Map.Entry)o;
return eq(key, e.getKey()) && eq(value, e.getValue());
}
public int hashCode() {
return ((key == null) ? 0 : key.hashCode()) ^
((value == null) ? 0 : value.hashCode());
}
public String toString() {
return key + "=" + value;
}
static boolean eq(Object o1, Object o2) {
return (o1 == null ? o2 == null : o1.equals(o2));
}
}
/* ---------------- Serialization Support -------------- */
/**
* Save the state of the <tt>ConcurrentHashMap</tt>
* instance to a stream (i.e.,
* serialize it).
* @param s the stream
* @serialData
* the key (Object) and value (Object)
* for each key-value mapping, followed by a null pair.
* The key-value mappings are emitted in no particular order.
*/
private void writeObject(java.io.ObjectOutputStream s) throws IOException {
s.defaultWriteObject();
for (int k = 0; k < segments.length; ++k) {
Segment seg = (Segment)segments[k];
seg.lock();
try {
HashEntry[] tab = seg.table;
for (int i = 0; i < tab.length; ++i) {
for (HashEntry e = (HashEntry)tab[i]; e != null; e = e.next) {
s.writeObject(e.key);
s.writeObject(e.value);
}
}
} finally {
seg.unlock();
}
}
s.writeObject(null);
s.writeObject(null);
}
/**
* Reconstitute the <tt>ConcurrentHashMap</tt>
* instance from a stream (i.e.,
* deserialize it).
* @param s the stream
*/
private void readObject(java.io.ObjectInputStream s)
throws IOException, ClassNotFoundException {
s.defaultReadObject();
// Initialize each segment to be minimally sized, and let grow.
for (int i = 0; i < segments.length; ++i) {
segments[i].setTable(new HashEntry[1]);
}
// Read the keys and values, and put the mappings in the table
for (;;) {
Object key = (Object) s.readObject();
Object value = (Object) s.readObject();
if (key == null)
break;
put(key, value);
}
}
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?