import java.util.Vector;
import java.util.LinkedList;
import java.util.Iterator;
import java.util.Enumeration;
 
public class Hashtable {
    Vector v;

    public Hashtable () {
	v = new Vector ();
	for (int i=0; i<1024; i++) {
	    v.add (new LinkedList ());
	}
    }

    public void put (Object key, Object value) {
	int hash = hash (key);
	LinkedList list = (LinkedList) v.get (hash);
        KeyValuePair kvp = findByKey (list, key);
	if (kvp == null) {
	    KeyValuePair pair = new KeyValuePair (key, value);
	    list.addFirst (pair);
	} else {
	    kvp.value = value;
	}
    }

    public Object get (Object key) {
	int hash = hash (key);
	LinkedList list = (LinkedList) v.get(hash);
        KeyValuePair kvp = findByKey (list, key);
	if (kvp == null) {
	    return null;
	} else {
	    return kvp.value;
	}
    }

    public Enumeration keys () {
	Vector keys = new Vector ();
	for (int i=0; i<v.size(); i++) {
	    LinkedList list = (LinkedList) v.get(i);
	    addKeys (list, keys);
	}
	return keys.elements ();
    }

    private KeyValuePair findByKey (LinkedList list, Object key) {
	Iterator it = list.iterator ();
	while (it.hasNext ()) {
	    KeyValuePair kvp = (KeyValuePair) it.next ();
	    if (kvp.key.equals (key)) return kvp;
	}
	return null;
    }

    private void addKeys (LinkedList list, Vector keys) {
	Iterator it = list.iterator ();
	while (it.hasNext ()) {
	    KeyValuePair kvp = (KeyValuePair) it.next ();
	    keys.add (kvp.key);
	}
    }

    private int hash (Object key) {
	int hash = key.hashCode () % v.size();
	if (hash >= 0) {
	    return hash;
	} else {
	    return hash + v.size();
	}
    }
}

class KeyValuePair {
    Object key, value;

    public KeyValuePair (Object key, Object value) {
	this.key = key;
	this.value = value;
    }

    public String toString () {
	return "{" + key + ", " + value + "}";
    }
}
