Tablas Hash en Java 1 – Hashtable vs HashMap

Hace poco hablábamos de la magia de las tablas Hash y su forma de almacenar la información, Java tiene una serie de tablas que usan una función Hash para el almacenamiento, hoy nos centraremos en dos: HashTable y HashMap.

Hashtable esta desde los comienzos de Java, nació en el JDK 1.0 (1996) y hoy en día se ha olvidado bastante en favor de HashMap, pero de todas formas es bueno tenerla en mente y conocer sus bondades y características.

A la hora de utilizar, HashMap y Hashtable es casi lo mismo; los dos implementan la interfaz Map y el desarrollador no notarán una gran diferencia.

Map<Integer, String> hashTable = new Hashtable<Integer, String>();
hashTable.put(1, "Madrid");
hashTable.put(2, "Barcelona");
hashTable.put(3, "Valencia");
Map<Integer, String> hashMap = new HashMap<Integer, String>();
hashMap.put(1, "Madrid");
hashMap.put(2, "Barcelona");
hashMap.put(3, "Valencia");

Aunque en el put si tenemos un detalle diferenciador, los HashMap aceptan claves nulas, pero los HashTable no, por ejemplo si haces lo siguiente:

Map<Integer, String> hashTable = new Hashtable<Integer, String>();
hashTable.put(1, "Madrid");
hashTable.put(2, "Barcelona");
hashTable.put(3, "Valencia");
hashTable.put(null, "Ciudad vacía");

Recibirás un fantástico NullPointerException por intentar meter un null como clave en la última línea.

Buscando alguna diferencia más, hay que destacar que Hashtable es seguro para usarse en modo multi-hilo, para lo cual HashMap no está preparado. Esto significa que un Hashtable se puede compartir en varios hilos a la vez sin problemas de concurrencia, pero hoy en día ni esta es una buena razón para utilizarlo, para esto, en Java 5 llegó una alternativa a HashMap llamado ConcurrentHashMap e incluso puedes convertir en sincronizado un HashMap utilizando la utilidad Collections y su buen método synchronizedMap.

Map<Integer, String> hashMap = new HashMap<Integer, String>();
Map<Integer, String> synchronizedMap = Collections.synchronizedMap(hashMap);
// Y con esto ya tenemos un hashMap listo para los multihilos.

Una vez presentados a los dos archienemigos Hashtable y HashMap, veamos como utilizarlos.

Como te comentaba, para añadir valores al mapa se hace con el método put(key, value) donde asociaremos un valor a una clave, con el método get(key) recuperamos el valor. Para recorrer el mapa en los dos casos se puede hacer con un forEach gracias al método values().

for (String ciudadMap : hashMap.values()) {
	System.out.println(ciudadMap);
}
//Mostramos las ciudades de un HashMap
for (Map.Entry<Integer, String> m:hashMap.entrySet()) { 
    System.out.println(m.getKey()+" "+m.getValue()); 
}

//Mostramos las ciudades de un HashTable
for (Map.Entry<Integer, String> t:hashTable.entrySet()) { 
    System.out.println(t.getKey()+" "+t.getValue()); 
} 

Hashtable además añade otra posibilidad de recorrerlo, usando el método elements(), que nos devuelve un enumerado de los valores.

Enumeration<String> elements = ((Hashtable<Integer, String>) hashTable).elements();
while (elements.hasMoreElements()) {
	System.out.println(elements.nextElement());
}

Si todavía no sabes por cual decantarte, darte como último detalle que LinkedHashMap hereda de HashMap. El punto clave de LinkedHashMap es que mantiene el orden de inserción, algo que no hace ni HashMap ni HashTable, por lo que si quieres mantener ese orden, es muy fácil cambiar uno por otro, con cambiar la implementación es suficiente.

Map<Integer, String> hashMap = new HashMap<Integer, String>();
hashMap.put(1, "Madrid");
hashMap.put(2, "Barcelona");
hashMap.put(3, "Valencia");
hashMap.put(44, "Sevilla");
hashMap.put(4, "Córdoba");

Esto muestra.

1 Madrid
2 Barcelona
3 Valencia
4 Córdoba
44 Sevilla

Con cambiar HashMap por LinkedHashMap se hace la magia y se muestra por orden de insercción.

Map<Integer, String> linkedHashMap = new LinkedHashMap<Integer, String>();
linkedHashMap.put(1, "Madrid");
linkedHashMap.put(2, "Barcelona");
linkedHashMap.put(3, "Valencia");
linkedHashMap.put(44, "Sevilla");
linkedHashMap.put(4, "Córdoba");
1 Madrid
2 Barcelona
3 Valencia
44 Sevilla
4 Córdoba

Resumiendo, a nivel de código HashMap y HashTable son muy parecidos, yo te aconsejo utilizar en el 99% de los casos HashMap y dejar HashTable como una divertida anécdota del pasado.

No quiero hacer spoilers, pero en próximos post hablaremos de más tablas Hash y otras peculiaridades del hashing muy divertidas como el HashCode. No te lo pierdas.

Dejar una contestacion

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *