KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > edu > rice > cs > util > BidirectionalHashMap


1 /*BEGIN_COPYRIGHT_BLOCK
2  *
3  * This file is part of DrJava. Download the current version of this project from http://www.drjava.org/
4  * or http://sourceforge.net/projects/drjava/
5  *
6  * DrJava Open Source License
7  *
8  * Copyright (C) 2001-2005 JavaPLT group at Rice University (javaplt@rice.edu). All rights reserved.
9  *
10  * Developed by: Java Programming Languages Team, Rice University, http://www.cs.rice.edu/~javaplt/
11  *
12  * Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated
13  * documentation files (the "Software"), to deal with the Software without restriction, including without limitation
14  * the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and
15  * to permit persons to whom the Software is furnished to do so, subject to the following conditions:
16  *
17  * - Redistributions of source code must retain the above copyright notice, this list of conditions and the
18  * following disclaimers.
19  * - Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the
20  * following disclaimers in the documentation and/or other materials provided with the distribution.
21  * - Neither the names of DrJava, the JavaPLT, Rice University, nor the names of its contributors may be used to
22  * endorse or promote products derived from this Software without specific prior written permission.
23  * - Products derived from this software may not be called "DrJava" nor use the term "DrJava" as part of their
24  * names without prior written permission from the JavaPLT group. For permission, write to javaplt@rice.edu.
25  *
26  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO
27  * THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
28  * CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
29  * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
30  * WITH THE SOFTWARE.
31  *
32  *END_COPYRIGHT_BLOCK*/

33
34 package edu.rice.cs.util;
35 import java.util.*;
36
37 public class BidirectionalHashMap<Type1, Type2> {
38   HashMap<Type1, Type2> forward = new HashMap<Type1, Type2>();
39   HashMap<Type2, Type1> backward = new HashMap<Type2, Type1>();
40   
41   public void put(Type1 key, Type2 value) {
42     if (forward.containsKey(key)) {
43       throw new IllegalArgumentException JavaDoc("Key " + key + " exists in hash already.");
44     }
45     if (forward.containsValue(value)) {
46       throw new IllegalArgumentException JavaDoc("Double hashes must be one to one. " + value + " exists already in hash.");
47     }
48     forward.put(key, value);
49     backward.put(value, key);
50   }
51   
52   public Type2 getValue(Type1 key) { return forward.get(key); }
53
54   public Type1 getKey(Type2 value) { return backward.get(value); }
55   
56   public boolean containsKey(Type1 key) { return forward.containsKey(key); }
57   
58   public boolean containsValue(Type2 value) { return backward.containsKey(value); }
59   
60   public Iterator<Type2> valuesIterator() { return new BHMIterator(); }
61   
62   public boolean isEmpty() { return forward.isEmpty(); }
63   
64   /** Returns a Collection<Type2> in some order. */
65   public Collection<Type2> values() { return forward.values(); }
66   
67   public Object JavaDoc[] valuesArray() { return values().toArray(); } // Return type should be Type2[]; type erasure bites!
68
public Type2[] valuesArray(Type2[] a) { return values().toArray(a); } // argument is hack to get the return type right
69

70   public Type2 removeValue(Type1 key) {
71     Type2 tmp = forward.remove(key);
72     backward.remove(tmp);
73     return tmp;
74   }
75   
76   public Type1 removeKey(Type2 value) {
77     Type1 tmp = backward.remove(value);
78     forward.remove(tmp);
79     return tmp;
80   }
81   
82   public int size() { return forward.size(); }
83  
84   
85   public void clear() {
86     forward = new HashMap<Type1, Type2>();
87     backward = new HashMap<Type2, Type1>();
88   }
89   
90   public String JavaDoc toString() {
91     String JavaDoc ret = "";
92     ret = "forward = " + forward.values() + "\nbackward = " + backward.values();
93     return ret;
94   }
95   
96   /** Iterator class for BiDirectionalHashMap */
97   class BHMIterator implements Iterator<Type2> {
98     
99     Iterator<Type2> forwardIt = forward.values().iterator();
100     
101     /** Cached value of last element returned by next() */
102     Type2 lastValue = null;
103     
104     public boolean hasNext() {
105       return forwardIt.hasNext();
106     }
107     
108     public Type2 next() {
109       lastValue = forwardIt.next();
110       return lastValue;
111     }
112     
113     /** Removes last element returned by next(); throws IllegalStateException if no such element */
114     public void remove() {
115       forwardIt.remove(); /* throws exception if lastValue is null */
116       backward.remove(lastValue); /* cannot fail because lastValue is not null */
117       lastValue = null;
118     }
119   }
120 }
121
Popular Tags