Map en Java, con ejemplos


imagesLa Interface Map (java.io.Map) en Java, nos permite representar una estructura de datos para almacenar pares "clave/valor"; de tal manera que para una clave solamente tenemos un valor. Esta estructura de datos también es conocida en otros lenguajes de programación como "Diccionarios", aunque en cada lenguajes esta estructura de datos tiene sus matices. Al igual que dijimos en la entrada de "ArrayList en Java, con ejemplos" los Maps en java tienen implimentada por debajo toda la teoría de las estructuras de datos de los Arboles (AVL, B, B+, B*) por tanto permiten añadir, eliminar y modificar elementos de forma trasparente para el programador. Antes de pasar a explicar el manejo de los Map, dejamos un enlace al JavaDoc, pulsando AQUI.

Antes de todo, decir que el código de todos los ejemplos que se ponen a continuación los podéis descargar pulsando AQUI.

Los principales métodos para trabajar con los Map son los siguientes:

// Declaración de un Map (un HashMap) con clave "Integer" y Valor "String". Las claves pueden ser de cualquier tipo de objetos, aunque los más utilizados como clave son los objetos predefinidos de Java como String, Integer, Double ... !!!!CUIDADO los Map no permiten datos atómicos
Map<Integer, String> nombreMap = new HashMap<Integer, String>();
nombreMap.size(); // Devuelve el numero de elementos del Map
nombreMap.isEmpty(); // Devuelve true si no hay elementos en el Map y false si si los hay
nombreMap.put(K clave, V valor); // Añade un elemento al Map
nombreMap.get(K clave); // Devuelve el valor de la clave que se le pasa como parámetro o 'null' si la clave no existe
nombreMap.clear(); // Borra todos los componentes del Map
nombreMap.remove(K clave); // Borra el par clave/valor de la clave que se le pasa como parámetro
nombreMap.containsKey(K clave); // Devuelve true si en el map hay una clave que coincide con K
nombreMap.containsValue(V valor); // Devuelve true si en el map hay un Valor que coincide con V
nombreMap.values(); // Devuelve una "Collection" con los valores del Map

Otro elemento importante a la hora de trabajar con los Maps (aunque no lo es tanto como a la hora de trabajar con los ArrayList) son los "Iteradores" (Iterator). Los Iteradores sirven para recorrer los Map y poder trabajar con ellos. Los Iteradores solo tienen tres métodos que son el “hasNext()” para comprobar que siguen quedando elementos en el iterador, el“next()”  para que nos de el siguiente elemento del iterador; y el “remove()” que sirve para eliminar el elemento del Iterador. En realidad se puede prescindir de los iteradores para trabajar con los Map ya que la gran ventaja de los Map frente a los ArrayList, es que estos tienen una clave asociada al objeto y se les puede buscar por la clave, aunque nunca esta de más saber utilizar los iteradores para manejar los Map.

Antes de seguir con ejemplos, os habréis dado cuenta que hemos empezado la entrada diciendo que Map es una Interface y por tanto se deben de implementar los métodos de la interface. Java ya tiene implementadas varias "clases Map". No vamos a explicar todas, pero si las tres que consideramos más importantes y útiles para que veáis la diferencia como son la clase "HashMap", "TreeMap" y "LinkedHashMap". La diferencia principal de estas 3 clases es la forma o el orden en las que guardan los valores en el Map. Si disteis en la carrera de Ingeniería Informática (o derivados) toda esa teoría de arboles (que no vamos a recordar aquí), veríais que la gran diferencia entre los arboles AVL, B, B+ y B* es la forma en la que guardan los datos para después optimizar las altas, bajas, modificaciones y consultas de los "valores". Pues bien toda esa teoría en esta entrada para nosotros es trasparente, pero esta bien que veamos estas tres clases para que en función de vuestro problema elijáis la mejor clase:

  • HashMap: Los elementos que inserta en el map no tendrán un orden específico. No aceptan claves duplicadas ni valores nulos.
  • TreeMap: El Mapa lo ordena de forma "natural". Por ejemplo, si la clave son valores enteros (como luego veremos), los ordena de menos a mayor.
  • LinkedHashMap: Inserta en el Map los elementos en el orden en el que se van insertando; es decir, que no tiene una ordenación de los elementos como tal, por lo que esta clase realiza las búsquedas de los elementos de forma más lenta que las demás clases.

Visto esto vamos a poner un ejemplo de estas 3 clases y como ordena los elementos. Para este ejemplo vamos a tener un Map en el que la clave va a ser el dorsal de los jugadores de fútbol de la selección española que jugaron de titulares la final de la copa del mundo de 2010, y su valor va a ser su nombre.

Con un HashMap

Map<Integer, String> map = new HashMap<Integer, String>();
map.put(1, "Casillas");		map.put(15, "Ramos");
map.put(3, "Pique");		map.put(5, "Puyol");
map.put(11, "Capdevila");	map.put(14, "Xabi Alonso");
map.put(16, "Busquets");	map.put(8, "Xavi Hernandez");
map.put(18, "Pedrito");		map.put(6, "Iniesta");
map.put(7, "Villa");

// Imprimimos el Map con un Iterador
Iterator it = map.keySet().iterator();
while(it.hasNext()){
  Integer key = it.next();
  System.out.println("Clave: " + key + " -> Valor: " + map.get(key));
}

El resultado que tenemos es el siguiente, en el que vemos que nos da los objetos sin un "orden lógico":

Clave: 16 -> Valor: Busquets
Clave: 1  -> Valor: Casillas
Clave: 18 -> Valor: Pedrito
Clave: 3  -> Valor: Pique
Clave: 5  -> Valor: Puyol
Clave: 6  -> Valor: Iniesta
Clave: 7  -> Valor: Villa
Clave: 8  -> Valor: Xavi Hernandez
Clave: 11 -> Valor: Capdevila
Clave: 14 -> Valor: Xabi Alonso
Clave: 15 -> Valor: Ramos

Con un TreeMap

Map<Integer, String> treeMap = new TreeMap<Integer, String>();
treeMap.put(1, "Casillas");	treeMap.put(15, "Ramos");
treeMap.put(3, "Pique");	treeMap.put(5, "Puyol");
treeMap.put(11, "Capdevila");	treeMap.put(14, "Xabi Alonso");
treeMap.put(16, "Busquets");	treeMap.put(8, "Xavi Hernandez");
treeMap.put(18, "Pedrito");	treeMap.put(6, "Iniesta");
treeMap.put(7, "Villa");

// Imprimimos el Map con un Iterador que ya hemos instanciado anteriormente
it = treeMap.keySet().iterator();
while(it.hasNext()){
  Integer key = it.next();
  System.out.println("Clave: " + key + " -> Valor: " + treeMap.get(key));
}

El resultado que tenemos es el siguiente en el que vemos que nos ordena los objetos por clave en "orden natural":

Clave: 1  -> Valor: Casillas
Clave: 3  -> Valor: Pique
Clave: 5  -> Valor: Puyol
Clave: 6  -> Valor: Iniesta
Clave: 7  -> Valor: Villa
Clave: 8  -> Valor: Xavi Hernandez
Clave: 11 -> Valor: Capdevila
Clave: 14 -> Valor: Xabi Alonso
Clave: 15 -> Valor: Ramos
Clave: 16 -> Valor: Busquets
Clave: 18 -> Valor: Pedrito

Con un LinkedHashMap

Map<Integer, String> linkedHashMap = new LinkedHashMap<Integer, String>();
linkedHashMap.put(1, "Casillas");	linkedHashMap.put(15, "Ramos");
linkedHashMap.put(3, "Pique");		linkedHashMap.put(5, "Puyol");
linkedHashMap.put(11, "Capdevila");	linkedHashMap.put(14, "Xabi Alonso");
linkedHashMap.put(16, "Busquets");	linkedHashMap.put(8, "Xavi Hernandez");
linkedHashMap.put(18, "Pedrito");	linkedHashMap.put(6, "Iniesta");
linkedHashMap.put(7, "Villa");

// Imprimimos el Map con un Iterador que ya hemos instanciado anteriormente
it = linkedHashMap.keySet().iterator();
while(it.hasNext()){
  Integer key = it.next();
  System.out.println("Clave: " + key + " -> Valor: " + linkedHashMap.get(key));
}

El resultado que tenemos es el siguiente en el que vemos que nos ordena los objetos tal y como los hemos ido introduciendo:

Clave: 1  -> Valor: Casillas
Clave: 15 -> Valor: Ramos
Clave: 3  -> Valor: Pique
Clave: 5  -> Valor: Puyol
Clave: 11 -> Valor: Capdevila
Clave: 14 -> Valor: Xabi Alonso
Clave: 16 -> Valor: Busquets
Clave: 8  -> Valor: Xavi Hernandez
Clave: 18 -> Valor: Pedrito
Clave: 6  -> Valor: Iniesta
Clave: 7  -> Valor: Villa

Una vez que hemos visto las diferencias entre unas clases de Map y otras, vamos a ver el funcionamiento de los métodos que hemos mencionado al principio:

System.out.println("********* Trabajando con los métodos de Map *********");
System.out.println("Mostramos el numero de elementos que tiene el TreeMap: treeMap.size() = "+treeMap.size());
System.out.println("Vemos si el TreeMap esta vacio : treeMap.isEmpty() = "+treeMap.isEmpty());
System.out.println("Obtenemos un elemento del Map pasandole la clave 6: treeMap.get(6) = "+treeMap.get(6));
System.out.println("Borramos un elemento del Map el 18 (porque fue sustituido): treeMap.remove(18)"+treeMap.remove(18));
System.out.println("Vemos que pasa si queremos obtener la clave 18 que ya no existe: treeMap.get(18) = "+treeMap.get(18));
System.out.println("Vemos si existe un elemento con la clave 18: treeMap.containsKey(18) = "+treeMap.containsKey(18));
System.out.println("Vemos si existe un elemento con la clave 1: treeMap.containsKey(1) = "+treeMap.containsKey(1));
System.out.println("Vemos si existe el valo 'Villa' en el Map: treeMap.containsValue("Villa") = "+treeMap.containsValue("Villa"));
System.out.println("Vemos si existe el valo 'Ricardo' en el Map: treeMap.containsValue("Ricardo") = "+treeMap.containsValue("Ricardo"));
System.out.println("Borramos todos los elementos del Map: treeMap.clear()");treeMap.clear();
System.out.println("Comprobamos si lo hemos eliminado viendo su tamaño: treeMap.size() = "+treeMap.size());
System.out.println("Lo comprobamos tambien viendo si esta vacio treeMap.isEmpty() = "+treeMap.isEmpty());

Como salida para todos los métodos ejecutados obtendremos la siguiente:

********* Trabajando con los métodos de Map *********
Mostramos el numero de elementos que tiene el TreeMap: treeMap.size() = 11
Vemos si el TreeMap esta vacio : treeMap.isEmpty() = false
Obtenemos un elemento del Map pasandole la clave 6: treeMap.get(6) = Iniesta
Borramos un elemento del Map el 18 (porque fue sustituido): treeMap.remove(18)Pedrito
Vemos que pasa si queremos obtener la clave 18 que ya no existe: treeMap.get(18) = null
Vemos si existe un elemento con la clave 18: treeMap.containsKey(18) = false
Vemos si existe un elemento con la clave 1: treeMap.containsKey(1) = true
Vemos si existe el valo 'Villa' en el Map: treeMap.containsValue("Villa") = true
Vemos si existe el valo 'Ricardo' en el Map: treeMap.containsValue("Ricardo") = false
Borramos todos los elementos del Map: treeMap.clear()
Comprobamos si lo hemos eliminado viendo su tamaño: treeMap.size() = 0
Lo comprobamos tambien viendo si esta vacio treeMap.isEmpty() = true

Otra de las cosas más útiles al trabajar con los Map es el recorrerlos como si fuese un ArrayList, y eso lo conseguimos de la siguiente forma. Si queremos obtener los pares clave/valor o solo las claves o los valores por separado (cuidado ahora estamos trabajando con el LinkedHashMap del ejemplo):

System.out.println("Foreach: Forma alternativa para recorrer los Map mostrando la Clave y el valor:");
for (Entry<Integer, String> jugador : linkedHashMap.entrySet()){
	Integer clave = jugador.getKey();
	String valor = jugador.getValue();
	System.out.println(clave+"  ->  "+valor);
}

Como salida a este fragmento de código tenemos lo siguiente (que son a los jugadores por orden de inserción en el Map):

Foreach: Forma alternativa para recorrer los Map mostrando la Clave y el valor:
1  ->  Casillas
15 ->  Ramos
3  ->  Pique
5  ->  Puyol
11 ->  Capdevila
14 ->  Xabi Alonso
16 ->  Busquets
8  ->  Xavi Hernandez
18 ->  Pedrito
6  ->  Iniesta
7  ->  Villa

Como vemos, lo que hace este "foreach" es ir dándonos uno a uno cada par clave valor. Por tanto, si obtuviésemos solo el valor, tendríamos el mismo efecto que si estuviésemos trabajando con ArrayList o Colecciones.

Visto las 3 clases más utilizadas del los Map y los métodos más importantes, vamos a poner un ejemplo más de como trabajar con los Map. Pero en esta ocasión el valor no será un objeto predefinido de Java, sino que será un objeto de la clase "JugadorSeleccion" que mostramos a continuación:

class JugadorSeleccion {

	private int dorsal;
	private String nombre;
	private String demarcacion;

	public JugadorSeleccion() {
	}

	public JugadorSeleccion(int dorsal, String nombre, String demarcación) {
		this.dorsal = dorsal;
		this.nombre = nombre;
		this.demarcacion = demarcación;
	}

	public int getDorsal() {
		return dorsal;
	}

	public void setDorsal(int dorsal) {
		this.dorsal = dorsal;
	}

	public String getNombre() {
		return nombre;
	}

	public void setNombre(String nombre) {
		this.nombre = nombre;
	}

	public String getDemarcación() {
		return demarcacion;
	}

	public void setDemarcación(String demarcación) {
		this.demarcacion = demarcación;
	}

	@Override
	public String toString() {
		return this.dorsal+"  --  "+this.nombre+"  --  "+this.demarcacion;
	}

}

En este ejemplo nos vamos a crear un TreeMap en la que la clave será el nombre del jugador y el valor será un objeto de la clase "JugadorSeleccion". El TreeMap lo declaramos de la siguiente forma y metemos en él los siguientes objetos:

System.out.println("********* TreeMap con Objetos y como Clave un String *********");
Map <String, JugadorSeleccion> jugadores = new TreeMap<String, JugadorSeleccion>();
jugadores.put("Casillas", new JugadorSeleccion(1, "Casillas", "Portero"));
jugadores.put("Ramos", new JugadorSeleccion(15, "Ramos", "Lateral Derecho"));
jugadores.put("Pique", new JugadorSeleccion(13, "Pique", "Central"));
jugadores.put("Puyol", new JugadorSeleccion(5, "Puyol", "Central"));
jugadores.put("Capdevila", new JugadorSeleccion(11, "Capdevila", "Lateral Izquierdo"));
jugadores.put("Xabi", new JugadorSeleccion(14, "Xabi Alonso", "Medio Centro"));
jugadores.put("Busquets", new JugadorSeleccion(16, "Busquets", "Medio Centro"));
jugadores.put("Xavi", new JugadorSeleccion(8, "Xavi Hernandez", "Centro Campista"));
jugadores.put("Pedrito", new JugadorSeleccion(18, "Pedrito", "Interior Izquierdo"));
jugadores.put("Iniesta", new JugadorSeleccion(6, "Iniesta", "Interior Derecho"));
jugadores.put("Villa", new JugadorSeleccion(7, "Villa", "Delantero"));

Si hacemos un "foreach" de este TreeMap, vamos a ver que el Map va a estar ordenado por orden alfabético de la clave. Es decir, por el nombre de los jugadores:

for (Entry<String, JugadorSeleccion> jugador : jugadores.entrySet()){
	String clave = jugador.getKey();
	JugadorSeleccion valor = jugador.getValue();
	System.out.println(clave+"  ->  "+valor.toString());
}

Como resultado de esta ejecución del código tenemos el siguiente:

Busquets   ->  16  --  Busquets        --  Medio Centro
Capdevila  ->  11  --  Capdevila       --  Lateral Izquierdo
Casillas   ->  1   --  Casillas        --  Portero
Iniesta    ->  6   --  Iniesta         --  Interior Derecho
Pedrito    ->  18  --  Pedrito         --  Interior Izquierdo
Pique      ->  13  --  Pique           --  Central
Puyol      ->  5   --  Puyol           --  Central
Ramos      ->  15  --  Ramos           --  Lateral Derecho
Villa      ->  7   --  Villa           --  Delantero
Xabi       ->  14  --  Xabi Alonso     --  Medio Centro
Xavi       ->  8   --  Xavi Hernandez  --  Centro Campista

Si nos definimos nuestras propias clases y trabajamos con ellas en los Map, hay que tener muy claro una importante premisa en la programación "No es lo mismo 'Iguales' que 'Lo mismo' ". Esto quiere decir, que si nos creamos un nuevo objeto de la clase "JugadorSelección" cuyos atributos son Iguales que un objeto que se encuentre en el Map y ejecutamos el método "ContainsValue" nos devolverá un "false como una casa". Porque aunque sean objetos iguales, no son los mismo objetos, y por tanto, no lo contendrá el Map. Es decir, que si hacemos lo siguiente nos devolverá un false, debido a que nuestro objeto 'villla' no será el mismo que está en el Map:

// Cuidado con comparar objetos que son iguales pero no son lo mismo
JugadorSeleccion villa = new JugadorSeleccion(7, "Villa", "Delantero");
System.out.println("Esta este objeto 'villa' en el Map: jugadores.containsValue(villa) = "+jugadores.containsValue(villa));

Como salida conseguiremos la siguiente:

Esta este objeto 'villa' en el Map: jugadores.containsValue(villa) = false

En cambio, si ejecutamos lo que viene a continuación, estaremos preguntando por un objeto que sí que está dentro del Map:

// En este caso si que estamos preguntando por el mismo objeto
JugadorSeleccion navas = new JugadorSeleccion(22, "Navas", "Extremo Derecho");
jugadores.put("Navas", navas);
System.out.println("Esta este objeto 'navas' en el Map: jugadores.containsValue(navas) = "+jugadores.containsValue(navas));

Y como salida mostrará lo que sigue:

Esta este objeto 'navas' en el Map: jugadores.containsValue(navas) = true

En lo relacionado con trabajar con objetos "propios" es lo único en lo que hay que tener cuidado. Aunque los que estéis acostumbrados a programar en lenguajes como C o C++ en los que hay que tener muchísimo cuidado con los punteros, ésto lo tendréis más que superado. Sobre el resto de métodos, a la hora de trabajar con objetos "propios", no hay mucho más que decir.

Cualquier duda sobre los Map, no dudéis en preguntarla dejando un comentario en la entrada o en el Foro.

Comparte esta entrada en:
Safe Creative #1401310112503
Map en Java, con ejemplos por "www.jarroba.com" esta bajo una licencia Creative Commons
Reconocimiento-NoComercial-CompartirIgual 3.0 Unported License.
Creado a partir de la obra en www.jarroba.com

76 thoughts on “Map en Java, con ejemplos”

  1. Hace mucho tiempo que buscaba esta información y lo encontré gracias al Ingeniero Iván Murillo, la verdad desde que entre a estudiar esta carrera, el fue la base de toda la informática. Gracias Ing. Iván Murillo no soy nada sin ti, Te quiero <3

  2. Empleando la clase HashMap() de la biblioteca de java (una implementación de tablas hash con un string de clave y un entero de valor): • Como podemos implementar un agenda de teléfonos. • Como podemos crear una función para insertar un nueva entrada en la agenda, tomando como entradas el nombre de la persona y su teléfono. • Como podemos obtener un número de teléfono a partir de un nombre.

    1. Hola Andrés.
      No hacemos ejercicios de clase, pero te podemos dar unas pistas:
      Si te piden de clave un texto (entendemos como el nombre) y de valor un número (entendemos el número de teléfono), lo tienes fácil con Map 😉

  3. Escriba un programa que almacene información formalmente de un conjunto; de ese conjunto se deben extraer los elementos y almacenarlos en un diccionario de datos; obviamente los no repetidos.
    Condiciones del ejercicio:
    Se debe tener como base un grupo de estudiantes que reciben dos cursos distintos (máximo 20 entre los dos).
    En dicho grupo de estudiantes en su totalidad, en los dos cursos hay materias distintas; es decir, existe la posibilidad de que un estudiante se pueda registrar en los dos grupos (por tanto equivale a aparecer en las dos listas).
    Considere usar la clase que le permite ingresar de forma ordenada los elementos (respetando la forma en la que ingresan), separe de preferencia en dos grupos los estudiantes; considere usar dos conjuntos por lo menos.
    Esos datos deben ser luegos almacenados en un Mapa o Diccionario de Datos a razón de poder consultarlos.
    Subir los archivos de los programas, para posterior revisión.
    Se permiten trabajos grupales de máximo 4 personas.
    Se encuentra en esta tarea adjunta una plantilla para que la puedan realizar.
    Grupo A (10 estudiantes) Materias: Física, Programación, Educación Física, Francés.
    Luis, Gabriel, Iván, Andrés, Andrea, Tatiana, Juan, Carlos, Rodrigo, Ivana.
    Grupo B (10 estudiantes) Materias: Teoría de la Evolución, Cocina, Inglés, Realidad Social.
    José, Gabriel, Andrés, Tatiana, Miguel, Patricio, David, Estela, Hernán, Luisa.

    Como se puede ver, hay estudiantes que están inscritos en los dos grupos, pero en las operaciones de conjuntos no se permite la duplicidad, por tanto realice las operaciones que permitan generar un solo listado y guardarlo luego en un mapa para generar una agenda de contactos y poder ubicar

    1. Hola Alejandro.
      No hacemos ejercicios, pero te puedo dar unas pistas:
      Puedes crear una clase Estudiante con lo que necesitas y luego gestionarlos con estructuras de datos como Map o List.

  4. hola como estas, he estado mirando tu pagina no se si me puedas guiar un poco es que tengo esto:

    private void listarDetalle(HttpServletRequest request, HttpServletResponse response)
    throws ServletException, IOException {
    response.setContentType(«application/json»);

    String solicitudesM_numero_solicitud = Utility.ckNull(request.getParameter(«Orden»));
    String solicitudesM_prefijo = Utility.ckNull(request.getParameter(«prefFac»));
    String solicitudesM_numero_solicitud_sin_prefijo = Utility.ckNull(request.getParameter(«NoFacSinPref»));
    Map responseMap = new HashMap();
    try{
    List DetalleProducto = consultas.listarDetalle(solicitudesM_numero_solicitud, solicitudesM_prefijo, solicitudesM_prefijo);
    if (DetalleProducto!=null) {
    responseMap.put(«status», «200»);
    responseMap.put(«DetalleProductomensaje», «hay registros»);
    responseMap.put(«listaDetalle»,DetalleProducto);
    String json = new Gson().toJson(responseMap);
    System.out.println(«LA LISTA DE PRODUCTO ES:» + json);
    out.println(json);
    } else {
    System.out.println(«ERROR – No hay registros»);
    responseMap.put(«status», «400»);
    responseMap.put(«mensaje», «No hay registros»);
    String json = new Gson().toJson(responseMap);
    }
    } catch (Exception e) {
    e.printStackTrace();
    responseMap.put(«mensaje», «EXCEPTION»);
    String json = new Gson().toJson(responseMap);
    }
    }

    pero al momento de validar el Json no se imprime nada es como si estuviera llegando nulo ….

    1. Buenas Elizabeth.
      A simple vista en el código no lo ve mal. Comprueba que es lo qué te está llegando de respuesta en el «response» porque puede que no esté llegando nada.

  5. Buenas, no se si corresponde la pregutna en este tutorial pero tegno el siguiente problema
    Es posible que a travez de Map u otra interfaz de Java tenga la posibilidad de tener dos claves asociadas a un valor, no quiciera cargar ese valor dos veces
    Por lo que enteindo actualmente deberia dejar el codigo así:
    map.put(«a», 45);
    map.put(«A», 45);
    map.put(«b», 34);
    map.put(«B», 34);

    Pero quiero dejarlo de esta manera:
    map.put(«a», «A», 45);
    map.put(«b», «B», 34);

    1. Buenas Amilcar.
      El put de map el primer parámetro es la clave y el segundo el valor. Para lo que quieres lo mejor sería de clave del map un número entero y de valor un listado al que ir concatenando los valores de la clave coincidente.

  6. Hola, muy buenas. Muy claro como lo presentas. aprovecho para plantearte un problema que tengo con HashMap.
    Veo un cambio de comportamiento usando HashMap que no logro explicármelo: Si uso un HashMap funciona tal cual explicas arriba => por cada nuevo «Integer» agrego un String al map asociado a ése índice:
    mapa.put(0, «Hola») => mapa.get(0) devuelve «Hola»
    mapa.put(1, «Mundo») => mapa.get(1) devuelve «Mundo», etc.
    Ahora bien: usando HashMap cada nueva entrada asocida a un incremento del índice reemplaza el objeto anterior por el que estoy agregando:
    mapa.put(0, Objeto0) => mapa.get(0) devuelve Objeto0
    mapa.put(1, Objeto1) => mapa.get(1) devuelve Objeto1 PERO !!! mapa.get(0) también devuelve Objeto1 (ya no 0)
    mapa.put(2, Objeto2) => mapa.get(2) devuelve Objeto2 PERO mapa.get(1) Y mapa.get(0) devuelven también Objeto2 (ya no ni 1 ni 0).
    etc.
    No me doy cuenta en donde estoy errando. ¿Me podrías echar un poco de luz por aquí?
    Desde ya Muchas Gracias. Néstor.

    1. Parece que la página me jugó una mala pasada. El primer caso es (anda bien) es un HashMap Integer, String … el segundo caso (no sé si anda mal o yo no puedo explicarlo) es HashMap Integer, Object[]

    2. Parece que estás remplazando el valor del puntero (hay algunas variables que devuelven un puntero y no un valor «copiado»). Depende del código, pero por lo que comentas, probablemente las variables Objeto0, Objeto1 y Objeto2 apuntan al mismo objeto que al modificarlo modificas el objeto al que apuntan las claves 0, 1 y 2 (que debe ser el mismo puntero). No sé si me explico, sino copia aquí el trozo de código donde haces esta inserción y lo vemos 😉

    3. Que tal..
      Me gustaría si alguien pudiera apoyarme a resolver el ordenamiento de un hashmap, quiero ordenarlo por medio de la clave, la situación es que la clave la obtengo de una consuta a la base de datos, y necesito que el hashmap se ordene tal y como vienen los datos de la base.

    4. No es problema del hash map se trata de que estas creando mal el objeto simplemente cada vez que vayas enviar el objeto asegurate de crear correctamente el objeto que vas a pasar al hash map Ejem:
      En este caso estoy enviando una clase como el valor
      Auto p1=new Auto(String marca, Integer Modelo);
      Mapa(Llave,p1);//Dependera del nombre de tus variables

  7. No dejéis de hacer tan bien vuestro trabajo. Llevo años recurriendo a vuestra web por mi mente olvidadiza y cuando vuelvo a leer cada explicación pienso…. ¡pero que grandes son estos tíos!

    Por favor, nunca perdáis esa vocación por compartir conocimientos.

    Un saludo.

  8. buenas tardes, como seria mejor implementar un sistema para la visualizacion y actualizacion de datos de estudiante ej. matricula/nombre/carrera/edad/#materias aprobadas/#materias reprobadas/promedio 201504123/Carlos arias/in-tel/20/10/2/6.8 ¿es mejor usar mapas o tablas de dispersion? por favor responderme

    1. HashMap utiliza tablas de dispersión (más información de Hash en http://jarroba.com/codigo-hash/). Si bien existe también el HashTable, la direfencia es que HashMap no es síncrono (malo para multitaréa) y HashTable sí lo es (bueno para multitaréa), sino vas a utilizar multitaréa es mucho mejor utilizar HashMap por velocidad (si no vas a utilizar Threads).

       

       

  9. Hola gracias por tus tutoriales, tengo las sigueinte duda, he creado el siguiente mapa Mapa<Integer,Clase>  y dentro de mi clase tengo Un arraylist, sin embargo cuando llamo este arraylist desde donde sea sólo me devuelve el último arraylist insertado, ¿qué puedo hacer?

  10. Hola a todos:

        Mi problema es que me interesa recorrer sólo una parte de un hashmap, desde una posición a otra. Pero no se cómo debo recorrerlo. ¿ Alguno me prodría echar una mano?

    Intento hacer esto pero no me saca bien los valores:

    private static Map<Integer, Tema> temasDB = new ConcurrentHashMap<Integer, Tema>();

    ……..

    //inicio es el valor desde el que quiero emprezar

    for (int i = inicio; i < temasDB.size(); i++) {

    resultado += temasDB.get(i) + ". " + temasDB.values().toArray()[i] + "\n";

    }

    Gracias de antemano.

    1. Hola Salva. Prueba mejor obteniendo un tipo de «Listado» con:

      miHashMap.entrySet()

      Obtienes Set que contiene Entry con que son objetos Pojo de clave y valor. De este modo puedes trabajar como si fuera un listado.

      También puedes convertirlo en Array con:

      miHashMap.entrySet().toArray()

  11. Al realizar : 

    while(it.hasNext()){
    Integer key = it.next();
    System.out.println("Clave: " + key + " -> Valor: " + map.get(key));

     

    No hace falta realizar un cast en la linea : Integer key = it.next();

    y que quedara de la siguiente forma : Integer key = (Integer) it.next(); ??

     

    Si no es asñi podríais comentarme el porque ? Gracias y un saludo.

  12. Hola, felicidades por las explicaciones, son muy claras. Tengouna duda. Estoy intentando convertir un map en un set pero me veo incapaz.

    He hecho un bucle, recorriendo los values del map, ahora pretendo instanciar un set para ir llenando el set con todos sus valores. ¿Como puedo hacerlo?

    Gracias y un saludo

    1. El método keySet() del HashMap te devuelve el Set: http://docs.oracle.com/javase/7/docs/api/java/util/HashMap.html#keySet()

    1. En Java no puedes pasar funciones. Si guardas en el Map un objeto y lo obtienes puedes llamar a sus funciones.

  13. Gracias por esta soberbia explicación de la interface Map. Buscando en inglés y resulta que ni punto de comparación con lo que he encontrado en vuestra página. Aunque he de decir que ya os conocía: explicasteis como nadie lo que es el polimorfismo y qué decir de los threads… Impagable.

     

    Quisiera dejaros un apunte (constructivo) por si quereis tomarlo en consideración: cuando bajas el código y lo abres en eclipse salta el error de los acentos. Es fácil corregirlo, pero a lo mejor alguna persona no lo ve tan fácil. Y hablo por mi cuando comenzaba en esto, cualquier error del editor recuerdo que era un mundo. 

     

    Gracias de nuevo por vuestras explicaciones.

  14. Hola,

    Sólo quería agradecer las aportaciones tan valiosas y desinteresadas que hacéis para la gente que empezamos en el mundo de java.

    Sois unos fieras, tan jóvenes y tanto conocimiento…

    Mis más sinceras felicitaciones.

  15. Excelente explicación, en caso de querer leer desde un archivo .txt los nombres delos jugadores que procedimiento seria utilizando los maps, espero me resuelvan esa duda, saludos.
    excelente blog.

    1. Solo tendrías que ir leyendo del fichero e ir guardando en el Map. Cuando tengas los datos en el Map utilizarías éste.

  16. Amigo son los Mejores Explicando
    Podrian Hacer un Post con La Interfaz Set ???
    Me seria de gran ayuda

  17. Excelente explicación!!

    Como puedo imprimir los datos de un valor a partir de su clave específica… Tomando en cuenta que los valores son Tipo objeto.
    Gracias!

    1. Hola Javier.
      Para ello debes de sobreescribir en la clase el método «toString()» como se ve en el último método de la clase «JugadorSeleccion».
      SL2

  18. Buen trabajo chicos!!!!

    Sólo comentaros que la Clase HashMap como bien comentáis no acepta claves duplicadas aunque si acepta null (sólo aceptaría uno porqué el segundo seria una duplicidad) y SI acepta null en lo referente a los valores, sin limitaciones.

    Enhorabuena por la web!!!

  19. Gracias Excelente pagina para alguien que esta empezando con Java y que me cuesta demasiado entender

    Yo tengo la situacion siguiente:
    un objeto que tiene como 5 atributos (siennndo uno de esstos el que se utilizara como clave) y 4 metodos

    he creado un map (String, objeto)
    al hacer map.put no me da problemaass
    no tengo problemas paraa compilar, pero al momento de ejecutar, ingreeso mi codiggo tipo string como clave, y al imprimir tengo algo assi:
    Clave: codigo
    Valores: vaariable objeto@d93b30

    Porque nno puedo ver el contenido de todos los atributos que le corressponden a esa clave.
    Puess lleugo quiero hacer una busqueda, y cuando ingreso la clave se me va por el mensaje programado de «no se encotraron registros

    1. Hola Teresa.
      Estas imprimiendo el objeto de tu map como tal y no los atributos del mismo. Mira como en la entrada sobre-escribo el método «toString» en la clase JugadorSeleccion:

      @Override
      public String toString() {
      return this.dorsal+» — «+this.nombre+» — «+this.demarcacion;
      }

      De esta forma imprime los atributos del objeto de tu map. Sobre la clase debes de asignar la clave al map aunque luego la tengas también en tu objeto, pero asegurate en asignarla al map para luego hacer bien la búsqueda.

      SL2

  20. Buenas tardes, me encantó las explicaciones, estoy comenzando en el mundo java y la verdad que me cuesta bastante todo eso y esta web me ha servido de mucha ayuda.
    Estoy tratando de realizar una gráfica con valores que ordene dentro de un HashMap, estoy teniendo problemas para poder sacar estos valores dentro del HashMap, de forma tal, que queden ordenados cada uno con el que le corresponde….si me pueden tirar alguna ayudita estaría agradecida. Gracias y saludos

  21. Muchisimas gracias por este tutorial que han preparado para nosotros, esta muy bien explicado, muy claro todo, con varios ejemplos, es lo que uno siempre quisiera encontrarse, muchas gracias por tomarse el tiempo de hacer estos tutoriales. Tengo una pregunta con respecto al TreeMap, si yo quisiera meter en el TreeMap un objeto como clave, como le hago para que me los ordene respecto a un criterio que yo especifique?? como en c++ que puedes sobrecargar el operador «<" para una determinada estructura, se puede hacer esto en java??. Gracias por todo.

    Saludos de otro nuevo seguidor!!

    1. Hola Martín.
      La verdad que lo que comentas nose si tiene sentido hacerlo con un Map, aunque poner como clave un objeto en principio se puede hacer aunque yo la verdad no lo he hecho nunca (salvo los String, Integer y demás que son los objetos de los datos atómicos por decirlo de alguna forma). El tema de la ordenación por clave es algo interno del tipo de Map que utilices. Si utilizas un TreeMap y tienes como clave un Integer, este te lo ordenará en orden, pero si pones como clave un objeto te lo ordenará según el criterio del TreeMap.

      En resumen lo que propones nose si se puede hacer. Quizas para hacer eso yo utilizaría un ArrayList y lo ordenaria según el atributo que quisieses. En esta web tienes una entrada de como ordenar un ArrayList: http://jarroba.com/ordenar-un-arraylist-en-java/

      SL2

    2. Buenas: si quieres ordenar objetos solo tienes que implementar la interfaz Comparable y definir el método compareTo() en la clase correspondiente; por ejemplo, para una clase MyTime:

      @Override //compareTo
      public int compareTo(MyTime f) {
      if(this.hour > f.hour)
      return 1;
      else if(this.hour f.minute)
      return 1;
      else if(this.minute < f.minute)
      return -1;
      else
      return 0;
      }
      }

      Si te he entendido mal y buscas otra cosa, te pido disculpas. Un saludo.

      1. Al copiar y pegar el código se ha perdido mucho texto, a ver si funciona ahora:

        @Override //compareTo
        public int compareTo(MyTime f) {
        if(this.hour > f.hour) {
        return 1;
        }
        else if(this.hour f.minute) {
        return 1;
        }
        else if(this.minute < f.minute) {
        return -1;
        }
        else { //this.hour == f. hour && this.minute == f.minute
        return 0;
        }
        }
        }

        Un saludo y perdona las molestias.

  22. hola, queria saber como puedo insertar objetos tanto el la clave como en el valor(bueno uno puede ser string), nesesito hacer un diccionario, y como puedo ordenarlos en base a un atributo del objeto, o de su clave, gracias…

    1. Buenas Kevin,

      Muy sencillo, puedes utilizar TreeMap (más información en: http://docs.oracle.com/javase/6/docs/api/java/util/TreeMap.html), su principal utilidad es que va ordenando las claves según las insertas. Un ejemplo rápido sería:
      Map<Integer, String> mapa = new TreeMap<Integer, String>();

      mapa.put(3, "aaa");
      mapa.put(1, "bbb");
      mapa.put(2, "ccc");

      Set<Entry<Integer, String>> s = mapa.entrySet();
      for (Entry<Integer, String> entry : s) {
      System.out.println(entry.getKey() + " -> " + entry.getValue());
      }

      La salida por pantalla ordenado por claves:

      1 -> bbb
      2 -> ccc
      3 -> aaa

  23. Buenas noches, quisiera saber si hay alguna forma de que el mapa almacene los valores de manera permanente en el programa es decir que funcione como una Session en java, de tal forma que pueda ser usado tambien en otra clase ademas de la misma de donde esta siendo usada gracias

    1. Buenas Willandher,

      Una opción es que crees el Map como una variable global y estática para acceder directamente a ésta desde cualquier parte del programa sin tener que instanciar la clase ni perder el valor guardado en ella (ten en cuenta que al cerrar el programa todo se borra, solo persisten mientras el programa esté en ejecución). También te puede interesar utilizar el patrón Singleton que sirve para estas cosas.

  24. Hola, una pregunta, si en un map queremos meter –>

    public int protagonizar (Film f, Collection ci)

    cuando map lo he declarado private Map; como se debe hacer? ya que el put da error. Gracias

      1. Hola Miguel Angel. No entiendo muy bien tu pregunta, pero si declaras un Map como private no tienes porque tener ningún problema siempre que trabajar en la misma clase en la que lo tienes declarado. Sino me das más datos no puedo ayudarte.

        Por otro lado recuerda que Map es una Interface por tanto debes de instanciar un HashMap, TreeMap, … o lo que sea, igual es eso lo que te da problemas.

        Con lo que me dices no puedo ayudarte, así que o me das más datos o el error puede venir de otro lado.

        Saludos

  25. He descubierto hoy vuestra web y me parece que, con diferencia, le dais mil vueltas al resto de webs que intentan explicar cosas de java.(Aún no he visto las entradas que tenéis de Android pero imagino que seguirán la misma línea)

    Explicaciones entendibles y con código que funciona!! Parecerá una tontería, pero no es nada fácil de encontrar.

    Enhorabuena, os animo a que sigáis destripando java de la forma en la que lo estáis haciendo.

    Saludos de un nuevo seguidor!!

    1. Hola Salva. Muchas Gracias por tus palabras. Poco a poco vamos sacando tutoriales de como hacer las cosas aunque lo vamos haciendo poco a poco porque no tenemos dedicación exclusiva a esta web. De todas formas tenemos idea de seguir sacando tutoriales de Java ya que tanto Ramón como yo tenemos mucha experiencia con este lenguaje.

      Gracias y Saludos

Deja una respuesta

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

Este sitio usa Akismet para reducir el spam. Aprende cómo se procesan los datos de tus comentarios.

Uso de cookies

Este sitio web utiliza cookies para que usted tenga la mejor experiencia de usuario. Si continúa navegando está dando su consentimiento para la aceptación de las mencionadas cookies y la aceptación de nuestra política de cookies

ACEPTAR
Aviso de cookies