001: /*
002: * Copyright 2003-2004 The Apache Software Foundation
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016: package org.apache.commons.collections;
017:
018: /**
019: * Defines a map that allows bidirectional lookup between key and values.
020: * <p>
021: * This extended <code>Map</code> represents a mapping where a key may
022: * lookup a value and a value may lookup a key with equal ease.
023: * This interface extends <code>Map</code> and so may be used anywhere a map
024: * is required. The interface provides an inverse map view, enabling
025: * full access to both directions of the <code>BidiMap</code>.
026: * <p>
027: * Implementations should allow a value to be looked up from a key and
028: * a key to be looked up from a value with equal performance.
029: * <p>
030: * This map enforces the restriction that there is a 1:1 relation between
031: * keys and values, meaning that multiple keys cannot map to the same value.
032: * This is required so that "inverting" the map results in a map without
033: * duplicate keys. See the {@link #put} method description for more information.
034: *
035: * @since Commons Collections 3.0
036: * @version $Revision: 155406 $ $Date: 2005-02-26 12:55:26 +0000 (Sat, 26 Feb 2005) $
037: *
038: * @author Stephen Colebourne
039: */
040: public interface BidiMap extends IterableMap {
041:
042: /**
043: * Obtains a <code>MapIterator</code> over the map.
044: * <p>
045: * A map iterator is an efficient way of iterating over maps.
046: * It does not require that the map is stored using Map Entry objects
047: * which can increase performance.
048: * <pre>
049: * BidiMap map = new DualHashBidiMap();
050: * MapIterator it = map.mapIterator();
051: * while (it.hasNext()) {
052: * Object key = it.next();
053: * Object value = it.getValue();
054: * it.setValue("newValue");
055: * }
056: * </pre>
057: *
058: * @return a map iterator
059: */
060: MapIterator mapIterator();
061:
062: /**
063: * Puts the key-value pair into the map, replacing any previous pair.
064: * <p>
065: * When adding a key-value pair, the value may already exist in the map
066: * against a different key. That mapping is removed, to ensure that the
067: * value only occurs once in the inverse map.
068: * <pre>
069: * BidiMap map1 = new DualHashBidiMap();
070: * map.put("A","B"); // contains A mapped to B, as per Map
071: * map.put("A","C"); // contains A mapped to C, as per Map
072: *
073: * BidiMap map2 = new DualHashBidiMap();
074: * map.put("A","B"); // contains A mapped to B, as per Map
075: * map.put("C","B"); // contains C mapped to B, key A is removed
076: * </pre>
077: *
078: * @param key the key to store
079: * @param value the value to store
080: * @return the previous value mapped to this key
081: *
082: * @throws UnsupportedOperationException if the <code>put</code> method is not supported
083: * @throws ClassCastException (optional) if the map limits the type of the
084: * value and the specified value is inappropriate
085: * @throws IllegalArgumentException (optional) if the map limits the values
086: * in some way and the value was invalid
087: * @throws NullPointerException (optional) if the map limits the values to
088: * non-null and null was specified
089: */
090: Object put(Object key, Object value);
091:
092: /**
093: * Gets the key that is currently mapped to the specified value.
094: * <p>
095: * If the value is not contained in the map, <code>null</code> is returned.
096: * <p>
097: * Implementations should seek to make this method perform equally as well
098: * as <code>get(Object)</code>.
099: *
100: * @param value the value to find the key for
101: * @return the mapped key, or <code>null</code> if not found
102: *
103: * @throws ClassCastException (optional) if the map limits the type of the
104: * value and the specified value is inappropriate
105: * @throws NullPointerException (optional) if the map limits the values to
106: * non-null and null was specified
107: */
108: Object getKey(Object value);
109:
110: /**
111: * Removes the key-value pair that is currently mapped to the specified
112: * value (optional operation).
113: * <p>
114: * If the value is not contained in the map, <code>null</code> is returned.
115: * <p>
116: * Implementations should seek to make this method perform equally as well
117: * as <code>remove(Object)</code>.
118: *
119: * @param value the value to find the key-value pair for
120: * @return the key that was removed, <code>null</code> if nothing removed
121: *
122: * @throws ClassCastException (optional) if the map limits the type of the
123: * value and the specified value is inappropriate
124: * @throws NullPointerException (optional) if the map limits the values to
125: * non-null and null was specified
126: * @throws UnsupportedOperationException if this method is not supported
127: * by the implementation
128: */
129: Object removeValue(Object value);
130:
131: /**
132: * Gets a view of this map where the keys and values are reversed.
133: * <p>
134: * Changes to one map will be visible in the other and vice versa.
135: * This enables both directions of the map to be accessed as a <code>Map</code>.
136: * <p>
137: * Implementations should seek to avoid creating a new object every time this
138: * method is called. See <code>AbstractMap.values()</code> etc. Calling this
139: * method on the inverse map should return the original.
140: *
141: * @return an inverted bidirectional map
142: */
143: BidiMap inverseBidiMap();
144:
145: }
|