package java.util;

import ej.annotation.Nullable;

/**
 * This class implements a hash table, which maps keys to values. Any non-<code>null</code> object
 * can be used as a key or as a value.
 * <p>
 *
 * To successfully store and retrieve objects from a hashtable, the objects used as keys must
 * implement the <code>hashCode</code> method and the <code>equals</code> method.
 * <p>
 *
 * An instance of <code>Hashtable</code> has two parameters that affect its performance: <i>initial
 * capacity</i> and <i>load factor</i>. The <i>capacity</i> is the number of <i>buckets</i> in the
 * hash table, and the <i>initial capacity</i> is simply the capacity at the time the hash table is
 * created. Note that the hash table is <i>open</i>: in the case of a "hash collision", a single
 * bucket stores multiple entries, which must be searched sequentially. The <i>load factor</i> is a
 * measure of how full the hash table is allowed to get before its capacity is automatically
 * increased. The initial capacity and load factor parameters are merely hints to the
 * implementation. The exact details as to when and whether the rehash method is invoked are
 * implementation-dependent.
 * <p>
 *
 * Generally, the default load factor (.75) offers a good tradeoff between time and space costs.
 * Higher values decrease the space overhead but increase the time cost to look up an entry (which
 * is reflected in most <code>Hashtable</code> operations, including <code>get</code> and <code>put</code>).
 * <p>
 *
 * The initial capacity controls a tradeoff between wasted space and the need for
 * <code>rehash</code> operations, which are time-consuming. No <code>rehash</code> operations will
 * <i>ever</i> occur if the initial capacity is greater than the maximum number of entries the
 * <code>Hashtable</code> will contain divided by its load factor. However, setting the initial capacity
 * too high can waste space.
 * <p>
 *
 * If many entries are to be made into a <code>Hashtable</code>, creating it with a sufficiently
 * large capacity may allow the entries to be inserted more efficiently than letting it perform
 * automatic rehashing as needed to grow the table.
 * <p>
 *
 * This example creates a hashtable of numbers. It uses the names of the numbers as keys:
 *
 * <pre>
 * {
 * 	&#064;code
 * 	Hashtable&lt;String, Integer&gt; numbers = new Hashtable&lt;String, Integer&gt;();
 * 	numbers.put(&quot;one&quot;, 1);
 * 	numbers.put(&quot;two&quot;, 2);
 * 	numbers.put(&quot;three&quot;, 3);
 * }
 * </pre>
 *
 * <p>
 * To retrieve a number, use the following code:
 *
 * <pre>
 * {
 * 	&#064;code
 * 	Integer n = numbers.get(&quot;two&quot;);
 * 	if (n != null) {
 * 		System.out.println(&quot;two = &quot; + n);
 * 	}
 * }
 * </pre>
 *
 * <p>
 * The iterators returned by the <code>iterator</code> method of the collections returned by all of this
 * class's "collection view methods" are <em>fail-fast</em>: if the Hashtable is structurally
 * modified at any time after the iterator is created, in any way except through the iterator's own
 * <code>remove</code> method, the iterator will throw a {@link ConcurrentModificationException}. Thus,
 * in the face of concurrent modification, the iterator fails quickly and cleanly, rather than
 * risking arbitrary, non-deterministic behavior at an undetermined time in the future. The
 * Enumerations returned by Hashtable's keys and elements methods are <em>not</em> fail-fast.
 *
 * <p>
 * Note that the fail-fast behavior of an iterator cannot be guaranteed as it is, generally
 * speaking, impossible to make any hard guarantees in the presence of unsynchronized concurrent
 * modification. Fail-fast iterators throw <code>ConcurrentModificationException</code> on a best-effort
 * basis. Therefore, it would be wrong to write a program that depended on this exception for its
 * correctness: <i>the fail-fast behavior of iterators should be used only to detect bugs.</i>
 *
 * @param <K>
 *        the type of the keys maintained by this map
 * @param <V>
 *        the type of the mapped values
 *
 * @see Object#equals(java.lang.Object)
 * @see Object#hashCode()
 * @see Hashtable#rehash()
 * @see Collection
 * @see Map
 * @see HashMap
 */
public class Hashtable<K, V> extends Dictionary<K, V> implements Map<K, V>, Cloneable, java.io.Serializable {

	/**
	 * Constructs a new, empty hashtable with a default initial capacity (11) and load factor (0.75).
	 */
	public Hashtable() {
		throw new RuntimeException();
	}

	/**
	 * Constructs a new, empty hashtable with the specified initial capacity and default load factor
	 * (0.75).
	 *
	 * @param initialCapacity
	 *        the initial capacity of the hashtable.
	 * @exception IllegalArgumentException
	 *            if the initial capacity is less than zero.
	 */
	public Hashtable(int initialCapacity) {
		throw new RuntimeException();
	}

	/**
	 * Constructs a new, empty hashtable with the specified initial capacity and the specified load
	 * factor.
	 *
	 * @param initialCapacity
	 *        the initial capacity of the hashtable.
	 * @param loadFactor
	 *        the load factor of the hashtable.
	 * @exception IllegalArgumentException
	 *            if the initial capacity is less than zero, or if the load factor is nonpositive.
	 */
	public Hashtable(int initialCapacity, float loadFactor) {
		throw new RuntimeException();
	}

	/**
	 * Constructs a new hashtable with the same mappings as the given Map. The hashtable is created with
	 * an initial capacity sufficient to hold the mappings in the given Map and a default load factor
	 * (0.75).
	 *
	 * @param t
	 *        the map whose mappings are to be placed in this map.
	 * @throws NullPointerException
	 *         if the specified map is null.
	 */
	public Hashtable(Map<? extends K, ? extends V> t) {
		throw new RuntimeException();
	}

	/**
	 * Clears this hashtable so that it contains no keys.
	 */
	@Override
	public void clear() {
		throw new RuntimeException();
	}

	/**
	 * Creates a shallow copy of this hashtable. All the structure of the hashtable itself is copied,
	 * but the keys and values are not cloned. This is a relatively expensive operation.
	 *
	 * @return a clone of the hashtable
	 */
	@Override
	public Object clone() {
		throw new RuntimeException();
	}

	/**
	 * Tests if some key maps into the specified value in this hashtable. This operation is more
	 * expensive than the {@link #containsKey containsKey} method.
	 *
	 * <p>
	 * Note that this method is identical in functionality to {@link #containsValue containsValue},
	 * (which is part of the {@link Map} interface in the collections framework).
	 *
	 * @param value
	 *        a value to search for
	 * @return <code>true</code> if and only if some key maps to the <code>value</code> argument in this
	 *         hashtable as determined by the <code>equals</code> method; <code>false</code> otherwise.
	 * @exception NullPointerException
	 *            if the value is <code>null</code>
	 */
	public boolean contains(Object value) {
		throw new RuntimeException();
	}

	/**
	 * Tests if the specified object is a key in this hashtable.
	 *
	 * @param key
	 *        possible key
	 * @return <code>true</code> if and only if the specified object is a key in this hashtable, as
	 *         determined by the <code>equals</code> method; <code>false</code> otherwise.
	 * @throws NullPointerException
	 *         if the key is <code>null</code>
	 * @see #contains(Object)
	 */
	@Override
	public boolean containsKey(Object key) {
		throw new RuntimeException();
	}

	/**
	 * Returns true if this hashtable maps one or more keys to this value.
	 *
	 * <p>
	 * Note that this method is identical in functionality to {@link #contains contains} (which predates
	 * the {@link Map} interface).
	 *
	 * @param value
	 *        value whose presence in this hashtable is to be tested
	 * @return <code>true</code> if this map maps one or more keys to the specified value
	 * @throws NullPointerException
	 *         if the value is <code>null</code>
	 */
	@Override
	public boolean containsValue(Object value) {
		throw new RuntimeException();
	}

	/**
	 * Returns an enumeration of the values in this hashtable. Use the Enumeration methods on the
	 * returned object to fetch the elements sequentially.
	 *
	 * @return an enumeration of the values in this hashtable.
	 * @see java.util.Enumeration
	 * @see #keys()
	 * @see #values()
	 * @see Map
	 */
	@Override
	public Enumeration<V> elements() {
		throw new RuntimeException();
	}

	/**
	 * Returns a {@link Set} view of the mappings contained in this map. The set is backed by the map,
	 * so changes to the map are reflected in the set, and vice-versa. If the map is modified while an
	 * iteration over the set is in progress (except through the iterator's own <code>remove</code>
	 * operation, or through the <code>setValue</code> operation on a map entry returned by the iterator)
	 * the results of the iteration are undefined. The set supports element removal, which removes the
	 * corresponding mapping from the map, via the <code>Iterator.remove</code>, <code>Set.remove</code>,
	 * <code>removeAll</code>, <code>retainAll</code> and <code>clear</code> operations. It does not support the
	 * <code>add</code> or <code>addAll</code> operations.
	 */
	@Override
	public Set<Map.Entry<K, V>> entrySet() {
		throw new RuntimeException();
	}

	/**
	 * Compares the specified Object with this Map for equality, as per the definition in the Map
	 * interface.
	 *
	 * @param o
	 *        object to be compared for equality with this hashtable
	 * @return true if the specified Object is equal to this Map
	 * @see Map#equals(Object)
	 */
	@Override
	public boolean equals(@Nullable Object o) {
		throw new RuntimeException();
	}

	/**
	 * Returns the value to which the specified key is mapped, or {@code null} if this map contains no
	 * mapping for the key.
	 *
	 * <p>
	 * More formally, if this map contains a mapping from a key {@code k} to a value {@code v} such that
	 * {@code (key.equals(k))}, then this method returns {@code v}; otherwise it returns {@code null}.
	 * (There can be at most one such mapping.)
	 *
	 * @param key
	 *        the key whose associated value is to be returned
	 * @return the value to which the specified key is mapped, or {@code null} if this map contains no
	 *         mapping for the key
	 * @throws NullPointerException
	 *         if the specified key is null
	 * @see #put(Object, Object)
	 */
	@Override
	@Nullable
	public V get(Object key) {
		throw new RuntimeException();
	}

	/**
	 * Returns the hash code value for this Map as per the definition in the Map interface.
	 *
	 * @see Map#hashCode()
	 */
	@Override
	public int hashCode() {
		throw new RuntimeException();
	}

	/**
	 * Tests if this hashtable maps no keys to values.
	 *
	 * @return <code>true</code> if this hashtable maps no keys to values; <code>false</code> otherwise.
	 */
	@Override
	public boolean isEmpty() {
		throw new RuntimeException();
	}

	/**
	 * Returns an enumeration of the keys in this hashtable.
	 *
	 * @return an enumeration of the keys in this hashtable.
	 * @see Enumeration
	 * @see #elements()
	 * @see #keySet()
	 * @see Map
	 */
	@Override
	public Enumeration<K> keys() {
		throw new RuntimeException();
	}

	/**
	 * Returns a {@link Set} view of the keys contained in this map. The set is backed by the map, so
	 * changes to the map are reflected in the set, and vice-versa. If the map is modified while an
	 * iteration over the set is in progress (except through the iterator's own <code>remove</code>
	 * operation), the results of the iteration are undefined. The set supports element removal, which
	 * removes the corresponding mapping from the map, via the <code>Iterator.remove</code>,
	 * <code>Set.remove</code>, <code>removeAll</code>, <code>retainAll</code>, and <code>clear</code> operations. It
	 * does not support the <code>add</code> or <code>addAll</code> operations.
	 */
	@Override
	public Set<K> keySet() {
		throw new RuntimeException();
	}

	/**
	 * Maps the specified <code>key</code> to the specified <code>value</code> in this hashtable.
	 * Neither the key nor the value can be <code>null</code>.
	 * <p>
	 *
	 * The value can be retrieved by calling the <code>get</code> method with a key that is equal to the
	 * original key.
	 *
	 * @param key
	 *        the hashtable key
	 * @param value
	 *        the value
	 * @return the previous value of the specified key in this hashtable, or <code>null</code> if it did
	 *         not have one
	 * @exception NullPointerException
	 *            if the key or value is <code>null</code>
	 * @see Object#equals(Object)
	 * @see #get(Object)
	 */
	@Override
	@Nullable
	public V put(K key, V value) {
		throw new RuntimeException();
	}

	/**
	 * Copies all of the mappings from the specified map to this hashtable. These mappings will replace
	 * any mappings that this hashtable had for any of the keys currently in the specified map.
	 *
	 * @param t
	 *        mappings to be stored in this map
	 * @throws NullPointerException
	 *         if the specified map is null
	 */
	@Override
	public void putAll(Map<? extends K, ? extends V> t) {
		throw new RuntimeException();
	}

	/**
	 * Increases the capacity of and internally reorganizes this hashtable, in order to accommodate and
	 * access its entries more efficiently. This method is called automatically when the number of keys
	 * in the hashtable exceeds this hashtable's capacity and load factor.
	 */
	protected void rehash() {
		throw new RuntimeException();
	}

	/**
	 * Removes the key (and its corresponding value) from this hashtable. This method does nothing if
	 * the key is not in the hashtable.
	 *
	 * @param key
	 *        the key that needs to be removed
	 * @return the value to which the key had been mapped in this hashtable, or <code>null</code> if the
	 *         key did not have a mapping
	 * @throws NullPointerException
	 *         if the key is <code>null</code>
	 */
	@Override
	@Nullable
	public V remove(Object key) {
		throw new RuntimeException();
	}

	/**
	 * Returns the number of keys in this hashtable.
	 *
	 * @return the number of keys in this hashtable.
	 */
	@Override
	public int size() {
		throw new RuntimeException();
	}

	/**
	 * Returns a string representation of this <code>Hashtable</code> object in the form of a set of
	 * entries, enclosed in braces and separated by the ASCII characters "<code>,&nbsp;</code>" (comma and
	 * space). Each entry is rendered as the key, an equals sign <code>=</code>, and the associated element,
	 * where the <code>toString</code> method is used to convert the key and element to strings.
	 *
	 * @return a string representation of this hashtable
	 */
	@Override
	public String toString() {
		throw new RuntimeException();
	}

	/**
	 * Returns a {@link Collection} view of the values contained in this map. The collection is backed
	 * by the map, so changes to the map are reflected in the collection, and vice-versa. If the map is
	 * modified while an iteration over the collection is in progress (except through the iterator's own
	 * <code>remove</code> operation), the results of the iteration are undefined. The collection supports
	 * element removal, which removes the corresponding mapping from the map, via the
	 * <code>Iterator.remove</code>, <code>Collection.remove</code>, <code>removeAll</code>, <code>retainAll</code> and
	 * <code>clear</code> operations. It does not support the <code>add</code> or <code>addAll</code> operations.
	 */
	@Override
	public Collection<V> values() {
		throw new RuntimeException();
	}
}