Foros del Web » Programación para mayores de 30 ;) » Java »

[SOLUCIONADO] Implementar TablaHash

Estas en el tema de Implementar TablaHash en el foro de Java en Foros del Web. Hola CalgaryCorpus estuve pensando y mucho en tus palabras pero no se me ocurre una forma de hacer los recorridos que no sea que los ...

  #31 (permalink)  
Antiguo 05/05/2017, 22:59
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus estuve pensando y mucho en tus palabras pero no se me ocurre una forma de hacer los recorridos que no sea que los datos están uno detrás del otro.

Lo peor de todo, es que estoy pensando en poner un atributo tipo entry llamado next para saber el siguiente cosa que no me gusta mucho la idea, pero no sé que hacer para llevar a cabo esto.

Código Java:
Ver original
  1. class Entry<K,V> implements Map.Entry<K,V>{
  2.         final K key;
  3.         V value;
  4.         Entry(K k, V v) {
  5.             value = v;
  6.             key = k;
  7.         }
  8.         @Override
  9.         public final K getKey() {
  10.             return key;
  11.         }
  12.         @Override
  13.         public final V getValue() {
  14.             return value;
  15.         }        
  16.         @Override
  17.         public V setValue(V v) {
  18.             V val = value;
  19.             value = v;
  20.             return val;
  21.         }
  22.         @Override
  23.         public String toString() {
  24.             return getKey() + " -> " + getValue();
  25.         }
  26.     }

Espero sus respuestas y saludos.
  #32 (permalink)  
Antiguo 06/05/2017, 09:02
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Si puedes identificar las casillas vacías de las ocupadas, puedes identificar el siguiente de cualquier elemento.
__________________
Visita mi perfil en LinkedIn
  #33 (permalink)  
Antiguo 06/05/2017, 22:41
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus de una forma rara encontré la solución, tuve que crear un método para encontrar el primer elemento:

Código Java:
Ver original
  1. private int firstIndex(){
  2.             int i = (size > 0) ? index : size;
  3.             for(; i< size; i++){
  4.                 if(table[i]!= null){
  5.                     return i;
  6.                 }
  7.             }
  8.             return i;
  9.         }

y unos cambios leves al recorrido:

Código Java:
Ver original
  1. public Entry<K,V> nextEntry() {
  2.             currEntry = nextEntry;
  3.             nextEntry = table[index];
  4.             index++;            
  5.             if (index <= size && table[index] != null) {
  6.                 nextEntry = table[index];              
  7.             } else {
  8.                 nextEntry = null;
  9.                 for (;index < size; index++){
  10.                     if (table[index] != null){
  11.                         nextEntry = table[index];
  12.                     }
  13.                 }
  14.             }
  15.             return currEntry;
  16.         }

Si me preguntarás si es pésima esta solución?? totalmente pero no se me ocurrió nada, dime ¿cómo cambiarías esta parte del código?

Espero sus respuestas y Saludos.
  #34 (permalink)  
Antiguo 07/05/2017, 09:26
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Si funciona, y lento, lo cambias.
else lo dejas.
Tienes que hacer pruebas, varias, independientes.
No 1 solo gran código que prueba de todo.
Ese era tu otro problema, tus pruebas. Mejora eso.
__________________
Visita mi perfil en LinkedIn
  #35 (permalink)  
Antiguo 07/05/2017, 13:09
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus, lo de las pruebas hice distintas en varios archivos cómo me dijiste además de deshacerme de firstIndex, pero en el dilema de que no me doy cuenta cómo mejorar los recorridos, sinceramente:

Código Java:
Ver original
  1. private abstract class HashIterator<E> implements Iterator<E> {
  2.         private int index = 0;
  3.         private Entry<K,V> currEntry = null;
  4.         private Entry<K,V> nextEntry = null;
  5.         /**
  6.          * Construye una nueva iteración hash
  7.          */
  8.         @SuppressWarnings("empty-statement")
  9.         HashIterator() {
  10.             index = 0;
  11.             for(; index< size; index++){
  12.                 if(table[index]!= null){
  13.                     nextEntry = table[index];
  14.                     break;
  15.                 }
  16.             }
  17.         }
  18.         /**
  19.          * Verifica si hay una siguiente entrada
  20.          *
  21.          * @return boolean -> verdadero o falso
  22.          */
  23.         @Override
  24.         public boolean hasNext() {
  25.             return nextEntry != null;
  26.         }
  27.         /**
  28.          * Obtiene la entrada próxima, y también es una función
  29.          * sobreexplotada para los recorridos ;)
  30.          *
  31.          * @return Entry<K,V> -> entrada clave/valor
  32.          */
  33.         @SuppressWarnings("empty-statement")
  34.         public Entry<K,V> nextEntry() {
  35.             currEntry = nextEntry;
  36.             nextEntry = table[index];
  37.             index++;            
  38.             if (index <= size && table[index] != null) {
  39.                 nextEntry = table[index];              
  40.             } else {
  41.                 nextEntry = null;
  42.                 for (;index < size; index++){
  43.                     if (table[index] != null){
  44.                         nextEntry = table[index];
  45.                     }
  46.                 }
  47.             }
  48.             return currEntry;
  49.         }
  50.     }

Espero sus respuestas y saludos.
  #36 (permalink)  
Antiguo 07/05/2017, 13:31
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

No me exprese' bien.
No hay nada que mejorar si no tienes un test que falla o que muestre algun problema.
Tienes algun test de este estilo? Hay algun test que falla?
Que estas probando en tus tests?

No tienes necesariamente que generar varios archivos con varios tests. Todos los tests pueden estar en 1 archivo, solo que tienen que estar en metodos distintos con nombres que indiquen que es lo que prueban. Cada test es o deberia ser (en general) independiente del otro.
__________________
Visita mi perfil en LinkedIn
  #37 (permalink)  
Antiguo 07/05/2017, 20:36
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus, en vista de lo que dijiste acabo de subir a github:

https://github.com/detectivejd/HassM.../hashmapsimple

y cómo en la vez anterior se agradecerá mucho las opiniones y críticas dadas al código, espero poder hacer un hashmap casero simple pero potente.

Espero sus respuestas y saludos.
  #38 (permalink)  
Antiguo 07/05/2017, 21:55
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Cuál test falla?
__________________
Visita mi perfil en LinkedIn
  #39 (permalink)  
Antiguo 07/05/2017, 22:24
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus, aparentemente ninguno, pero quedé rayado con el HashIterator con lo del nextEntry en la clase MyMap.

Viste que traté de hacer las correcciones que me dijiste??

Saludos.
  #40 (permalink)  
Antiguo 08/05/2017, 00:01
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Es interesante que digas que "aparentemente" ninguno falla.
Los tests que muestras estan construidos para generar en su salida alguna informacion, y es quien ejecuta el test que tiene que leer y darse cuenta si lo mostrado tiene sentido. Al menos eso es lo que note.

Hechos asi, los tests estan mal construidos. Los tests tienen que probar algo y mostrar un resultado. El test pasa o no pasa. Hay libraries que permiten probar e.g. JUnit, pero si no quieres usarla, al menos construye los tests para que ellos mismos prueben que lo que hiciste esta bien.

ejemplo de test:

Código:
void SI_hash_vacio_CUANDO_inserto_3_elementos_ENTONCES_hash_tiene_tamano_3() {
  // SI ..
  final MiHash h = new MiHash();

  // CUANDO ..
  h.add(clave1, valor1);
  h.add(clave2, valor2);
  h.add(clave3, valor3);

  // ENTONCES ..
  asegurar( h.size() == 3 );
  <indicar que el test tuvo exito>
}

void asegurar(final boolean condicion) {
   if(condicion == false) {
       <mostrar mensaje de error> o bien
       <arrojar una exception> 
   }
}
No hagas un menu para probar, ejecuta todas las pruebas todas las veces.
Elimina todos los System.out.println() de tus tests, no son necesarios.

Los nombres de los tests tienen que indicar lo que prueban.
De este modo, uno puede enumerar exactamente lo que estan probando.
Malos nombres: GetItemTest, RemoveItemTest, etc.
Mejores nombres: SI_hay_1_entry_CUANDO_se_inserta_igual_clave_ENTON CES_segundo_entry_reemplaza_al_primero
SI_hash_tiene_10_elementos_CUANDO_remuevo_3_elemen tos_ENTONCES_hash_tiene_tamano_7
etc

Los tests tienen que ser sencillos y probar 1 sola cosa.

Olvidate de optimizar tu recorrido. Mejora tus tests primero y ante la pregunta de si tus tests funcionan, tu respuesta tiene que ser si o no. No puede ser que "aparentemente" funcionan. Con buenos nombres sera facil decir que cosas estas probando y recibir sugerencias de que cosas te falta probar.

Como sabes si tus tests son suficientes?
A veces es conveniente medir cuanto del codigo que escribiste esta siendo probado por algun test. Si existe parte del codigo del hashmap que ningun test ejercita, o borras el codigo o construyes un test que lo pruebe.
__________________
Visita mi perfil en LinkedIn

Última edición por CalgaryCorpus; 08/05/2017 a las 06:40
  #41 (permalink)  
Antiguo 08/05/2017, 20:53
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus, le hice los cambios que me dijiste, espero haberlos hecho bien, aunque entre dicho cambios encontré un error bastante interesante y es en la parte de borrado de datos (DownTest.java) porque resulta que no me borra bien los datos, y no sé si el error está en la función remove o getIndex o en el HashIterator.

Me da cómo para replantearmelo.

https://github.com/detectivejd/HassM.../hashmapsimple

Espero sus respuestas y saludos.
  #42 (permalink)  
Antiguo 08/05/2017, 22:36
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Tus tests siguen llenos de System.out.println. No hiciste lo que te propuse. Sugiero vuelvas a leer lo anterior y ponerlo en práctica. De otra manera, seguiremos iterando hasta el infinito.
__________________
Visita mi perfil en LinkedIn
  #43 (permalink)  
Antiguo 09/05/2017, 20:48
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus espero haberlo hecho bien esta vez, pero el del remove sigue dando fallas en la parte de claves inexistentes, y más cuando traté de ver lo de los listados que me listaba cualquier cosa menos lo deseado al borrar.

https://github.com/detectivejd/HassM.../hashmapsimple

También digan si falta algún test que no haya tenido en cuenta.

Espero sus respuestas y saludos.
  #44 (permalink)  
Antiguo 09/05/2017, 21:33
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Los tests estan mal. En 1 prueba se prueba 1 sola cosa, si se llegara a probar mas de 1 cosa, deberian ser al menos cosas relacionadas, que colaboran entre si, que se modifican juntas, etc, pero NO cosas contradictorias.

Es raro ver, en un mismo test.
this.check(m3.size() == 4);
this.check(m3.isEmpty());

si lo primero tiene exito, lo segundo fracasara'. La prueba pasa?

O bien en otro test:

this.check(m4.size() == 4);
this.check(m4.size() == 1);

como esto puede darte buenos resultados? ejecutaste las pruebas? esta prueba pasa? Como haces para que un objeto diga que tiene 4 elementos y luego diga que tiene 1 elemento, sin haber hecho cambios y que ese test pase?

Una sugerencia: Si todas tus pruebas, dentro de una misma clase usan el mismo tipo de mapa, define un campo de ese tipo, refactoriza el codigo, creando un metodo que lo inicialice, y ese metodo lo llamas en cada test. Luego usas el objeto, ya inicializado. El codigo de tus tests se va a reducir un monton con esto. Al final de cada test borras el contenido del hash, si es necesario borrarlo, o cada vez que inicializas partes borrando todo.

En otro codigo encuentro esto:

System.out.println("\t ---PROBANDO VERIFICACIÓN CON CLAVES NULAS---");
System.out.println(" ");
this.check(col.containsKey(1));
this.check(col.containsKey(null));
this.check(col.containsKey(5));
this.check(col.containsKey(null));

suponiendo que el texto que pusiste es lo que quieres probar, para que incluyes containsKey(1) ? no estabas probando claves nulas? esperas que containsKey(null) sea true o false? la prueba parece que va a funcionar si containsKey(null) es true, es eso lo que esperas? para que lo invocas una segunda vez todo? esperas que el resultado cambie?

Otra sugerencia: Cambia tu implementacion de get(), completamente, para probar cuan bien estan tus pruebas. En la nueva implementacion, retorna siempre el mismo valor, no importa cual sea la clave que te pasan, por ejemplo, retorna "CalgaryCorpus", siempre siempre.
Aun pasan tus pruebas? Esperas que tus pruebas pasen o que fracasen?
Un hash que siempre retorna lo mismo, no importa la clave es un mal hash, de modo que las pruebas deberian detectar ese mal comportamiento.

Que tal si insertas los valores con las claves desordenadas? o que las claves sean numeros gigantescos? numeros primos? numeros pares? negativos? 0?

que pasa si insertas 2 veces el mismo par clave/valor?

que pasa si pides una clave justo despues de crear un hash?
de que tamano es un hash recien creado?

que pasa si iteras sobre un hash recien creado?
que valores esperas tener en un recorrido si has insertado 1 elemento? 2? 3? y luego, que valores esperas obtener si eliminas 1 elemento de un hash que tiene 1 elemento? que tiene 2? que tiene 3? (si borras el primero, el ultimo, el del medio)?

Las pruebas son independientes de tu implementacion. Que es lo que esperas recibir para cada accion.

Te habia dicho que no imprimas nada? que elimines los System.out.println? Sugiero que en vez de escribir, arrojes una exception y esta sea capturada y el stack trace escrito cuando la prueba fracase, en el stack trace va a estar el nombre de la funcion que fracaso. No es necesario el System.out.println, No es necesario escribir nada si la prueba pasa.

Ah! Otra cosa: Elimina los System.out.println de tus pruebas.
__________________
Visita mi perfil en LinkedIn
  #45 (permalink)  
Antiguo 09/05/2017, 23:05
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus acá hice un poco de lo que me dijiste, espero haber dado en el blanco aún así sigo viendo problemas con el remove.

https://github.com/detectivejd/HassM.../hashmapsimple

Reitero lo dicho: digan si falta algún test que no haya tenido en cuenta.

Espero sus respuestas y saludos.
  #46 (permalink)  
Antiguo 10/05/2017, 01:12
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Cita:
Iniciado por detective_jd Ver Mensaje
acá hice un poco de lo que me dijiste, ...
Avisa cuando lo hayas completado.
__________________
Visita mi perfil en LinkedIn
  #47 (permalink)  
Antiguo 10/05/2017, 20:43
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus me faltaron 2 cosas que te quiero preguntar:

Cita:
Te habia dicho que no imprimas nada? que elimines los System.out.println? Sugiero que en vez de escribir, arrojes una exception y esta sea capturada y el stack trace escrito cuando la prueba fracase, en el stack trace va a estar el nombre de la funcion que fracaso. No es necesario el System.out.println, No es necesario escribir nada si la prueba pasa.
¿Te refieres a que ponga un try y un catch en cada test?

Cita:
Otra sugerencia: Cambia tu implementacion de get(), completamente, para probar cuan bien estan tus pruebas. En la nueva implementacion, retorna siempre el mismo valor, no importa cual sea la clave que te pasan, por ejemplo, retorna "CalgaryCorpus", siempre siempre.
Aun pasan tus pruebas? Esperas que tus pruebas pasen o que fracasen?
Un hash que siempre retorna lo mismo, no importa la clave es un mal hash, de modo que las pruebas deberian detectar ese mal comportamiento.
Me queda hacer eso.

Pero el resto está hecho: https://github.com/detectivejd/HassM.../hashmapsimple

Reitero lo dicho: digan si falta algún test que no haya tenido en cuenta, xq pude haberme olvidado.

Espero sus respuestas y saludos.
  #48 (permalink)  
Antiguo 11/05/2017, 20:08
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus, hice lo de las excepciones y para ponerme a hacer lo que me dijiste del get, necesito que me responder lo siguiente:

Código Java:
Ver original
  1. @Override
  2.     public V get(Object key) {        
  3.         return (this.getEntry(key) == null) ? null : this.getEntry(key).getValue();
  4.     }
  5. private Entry<K, V> getEntry(Object key) {
  6.         int index = getIndex(key);
  7.         if(table[index] != null){
  8.             if (table[index].getKey().equals(key)){
  9.                 return table[index];
  10.             }            
  11.         }
  12.         return null;
  13.     }

tengo que cambiar así:

private Entry<K, V> getEntry(Object key) {
int index = getIndex(key);
if(table[index] != null){
if (table[index].getKey().equals(key)){
return "detective";
}
}
return null;
}

porque no me quedo muy claro esa parte.

Por otro lado, hasta ahora lo que voy detectando de errores es que al eliminar el listado me hace cualquier cosa, es decir: si elimino 3 elementos me muestra 2 en lugar de 3., que no sé si es problema del recorrido o que.

aquí, está la actualización del repositorio: https://github.com/detectivejd/HassM.../hashmapsimple

Espero sus respuestas y saludos.
  #49 (permalink)  
Antiguo 11/05/2017, 23:09
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

No te dije que capturaras excepciones, te dije que las arrojaras, sugiero que leas bien las sugerencias. Arrojar y capturar no es lo mismo. Incluso te puse un pseudo codigo antes:

Busca esto antes, para que veas lo que sugiero.

Código C:
Ver original
  1. void asegurar(final boolean condicion) {
  2.    if(condicion == false) {
  3.        <mostrar mensaje de error> o bien
  4.        <arrojar una exception>
  5.    }
  6. }

Como abusas de escribir, mejor olvida que dije que mostraras un mensaje de error. Arroja una excepcion, mejor.
En este momento tus tests no estan probando nada parece. No hay chequeos. Eso esta mal.

No tienes que poner try y catch, tienes que:
- chequear algo, 1 cosa por test y
- si esa condicion no se cumple, entonces se arrojara una excepcion,

si no la capturas, el programa testeador se caera' y solo -sin ayuda - escribira el stacktrace de la ejecucion y se terminara en ese momento.

Necesitas mas? No creo, porque si tienes 1 test malo o 10 malos, los vas resolviendo de a 1.

No le pongas "check" a tu funcion chequeadora, porque claramente en tus versiones anteriores no eras consistente con lo que querias probar. Si se elimina algo, por ejemplo, y yo vuelvo a buscar eso que busque', que esperarias que ocurriera? No me respondas, escribe eso que esperas como la condicion a chequear en la funcion "asegurar" que mostre mas arriba. La puedes renombrar a algo como "comprobar_que", para que el codigo sea facil de leer, si te parece.

Imagina este codigo, inventado por mi, para demostrar el punto.

Código:
inserto(clave, valor, hash)
comprobar_que( hash.get(clave) == valor )
borro(clave, hash )
comprobar_que( hash.get(clave) == null )
estas lineas pueden ser 2 tests, escrito en pseudo pseudo codigo.

Código:
test1: compruebo que lo que inserto, esta en el hash
{
  crear hash
  inserto(clave, valor, hash)
  comprobar_que( hash.get(clave) == valor )
}
Código:
test2: compruebo que despues de borrar, el elemento ya no esta
{
  crear hash
  inserto(clave, valor, hash)
  borro(clave, hash )
  comprobar_que( hash.get(clave) == null )
}
La sintaxis es inventada, solo para demostrar lo que se supone tienes que hacer.

Nota que las primera lineas del test2 es igual que el test1, pero en el test2 no comprobe si la clave estaba en el hash, por que? porque de eso se trataba el test1, no necesito probarlo en el test2.

Ahora, el test1 puede ser uno de varios. Para comprobar que lo que insertas esta, hay que hacer muchas pruebas, no solo 1, pero todas tienen que ser sencillas y suponer o tratar de suponer que las otras pruebas pasan. Es ahi, donde entra a jugar esto de que las claves sean impares, primos, etc. solo para stressar a tu estructura de datos.

Si tuvieras una funcion que inserta los valores de un arreglo al hash, podrias construir tests asi:

crear hash
insertar a hash el contenido del arreglo de primos
recorrer los elementos y comprobar que cada uno de los elementos que provienen del recorrido estan presentes en el arreglo (o al reves, pero para probar el recorrido, mejor usar el recorrido para iterar)

otro test
crear hash
insertar a hash el contenido del arreglo de pares
recorrer los elementos y comprobar que cada uno de los elementos que provienen del recorrido estan presentes en el arreglo .

otro test
crear hash
insertar a hash el contenido del arreglo de impares
recorrer los elementos y comprobar que cada uno de los elementos que provienen del recorrido estan presentes en el arreglo .

otro test
crear hash
insertar a hash el contenido del arreglo de numeros decrecientes
recorrer los elementos y comprobar que cada uno de los elementos que provienen del recorrido estan presentes en el arreglo

bueno y dado que esto parece ser el mismo test, por que no hacer 1 solo test de esto y llamarlo varias veces?

Código:
  probar_insercion( arreglo ){
     crear hash
     // insertar
     para cada elemento del arreglo( a -> hash.insert(a, "valor:" + a) )
     // comprobar
     para cada elemento del hash( k, v -> comprobar_que( k esta en el arreglo ) )
  }
y luego

Código:
probar_insercion( primos )
probar_insercion( pares )
probar_insercion( crecientes )
etc.
Ultima cosa, no pongas ningun mensaje ni hagas ninguna celebracion en el codigo cuando los tests pasan, solo genera una excepcion si un test falla.

Te habia mencionado que no escribas nada? Bueno, ahora te digo que no realices accion alguna si el test pasa exitosamente, nada. nada. nada. Si quieres, al final de toda la ejecucion, dices "Se acabo", "ejecucion terminada" o algo parecido. Todo el resto funciona o arroja una excepcion.
__________________
Visita mi perfil en LinkedIn
  #50 (permalink)  
Antiguo 13/05/2017, 21:44
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus espero esta vez haberlo hecho bien esta vez, me arroja excepciones cuando hago algo con los nulll de lo contrario no lo hace.

el repositorio está actualizado: https://github.com/detectivejd/HassM.../hashmapsimple

Espero sus respuestas y saludos.

PD: Hoy en mi país es el día de las madres, así que a todas las mamás feliz día :).
  #51 (permalink)  
Antiguo 14/05/2017, 00:58
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Estan mejor, pero no esta completo.

Por que mantienes tus System.out.println? Si la audiencia ha seguido este thread hasta aqui, recordara' que te he dicho varias veces que los elimines. No tienen nada que hacer en pruebas automatizadas. Pero bueno, me rindo, aqui tambien se acaba mi ayuda.

Ok, ultimas cosas: Tus pruebas siguen malas. Las pruebas de get todas comprueban que el valor es != null, no me hiciste caso de cambiar la implementacion de get para que te dieras cuenta que tus tests estan malos.
Las pruebas tienen que ser independientes entre si. Hay algunas pruebas que usan una variable col que no se define alli, y no se ve donde esta definida. Cada test tiene que definir y usar sus propios datos, nada de compartir con nadie.

Hay varias cosas mas, pero ... Me doy. Suerte con las modificaciones finales.
__________________
Visita mi perfil en LinkedIn
  #52 (permalink)  
Antiguo 14/05/2017, 14:51
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola CalgaryCorpus ante todo tengo que agradecerte por toda tu ayuda ya que gracias a tí mi map casero no tendría la eficiencia que hoy por hoy tiene pero también tengo cosas por decirte:

Cita:
Por que mantienes tus System.out.println? Si la audiencia ha seguido este thread hasta aqui, recordara' que te he dicho varias veces que los elimines. No tienen nada que hacer en pruebas automatizadas. Pero bueno, me rindo, aqui tambien se acaba mi ayuda.
Admito que me he olvidado y le he dado poca importancia a los println, xq quería ver lo de las pruebas, pero ¿sabés que? me deshice de todos ellos, pero no te rindas con esto ya que a mí no se me hubiera ocurrido ni la mitad de las sugerencias que me diste además está implementación es muy importante para mí ya que es una antesala de lo que realmente quiero hacer.
Además estamos implementado un map cosa que la mayoría ignora porque cómo Oracle lo tiene hecho se pierde el interés en su implementación.
Y estoy convencido al 100% de que si tenemos el HashMap bien implementado sacaremos el HashSet enseguida, pero para ello no puedo hacer esto sólo.

Cita:
Ok, ultimas cosas: Tus pruebas siguen malas. Las pruebas de get todas comprueban que el valor es != null, no me hiciste caso de cambiar la implementacion de get para que te dieras cuenta que tus tests estan malos.
¿En dónde están !=null? ¿En GetTest o en UpTest? xq en GetTest sólo en la normal están como dices, por otro lado no se me ocurre cómo cambiar la implementación de get además de obtener el índice y preguntar si coincide la clave pasada por parámetro con la clave del contenido del array del índice obtenido.
También me he dado cuenta que getIndex no funciona y me di cuenta con una prueba del remove y espero que al depurar está linea te des cuenta:

Código Java:
Ver original
  1. probando_borrado(restart1(), new Object[]{7,9});

al no andar bien getIndex, no funcionaría bien put (addEntry e putAll), getEntry ( containsKey e get), remove y lo peor de todo es que tampoco se me ocurre cómo cambiar lo del hashCode (y eso que miré en internet e intenté adaptar lo visto al código).

Cita:
Hay algunas pruebas que usan una variable col que no se define alli, y no se ve donde esta definida. Cada test tiene que definir y usar sus propios datos, nada de compartir con nadie.
Eso ya está hecho.

Sí a alguien le interesa el código acá está: https://github.com/detectivejd/HassM.../hashmapsimple

No lo he dicho antes pero si quieren modificarlo, adelante.

Espero sus respuestas y saludos.
  #53 (permalink)  
Antiguo 16/05/2017, 18:36
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola a todos, resulta que encontré una solución con lo del hashCode:

una función para calcular el hashCode según la clave pasada por parámetro:

Código Java:
Ver original
  1. private int hash(Object key) {
  2.         // hace el calculo del hashcode
  3.         int mod = key.hashCode() % table.length;
  4.         // si dicho calculo es menor, le sumas el tamaño del array, de lo contrario lo dejas tal como estás
  5.         return mod < 0 ? mod + table.length : mod;
  6.     }

Otra función para el tema de los índices y por si acaso:

Código Java:
Ver original
  1. private int getIndex(Object key) {
  2.         int index = hash(key);
  3.         while (table[index] != null && !table[index].getKey().equals(key)) {
  4.             index = (index + 1) % table.length;
  5.         }
  6.         return index;
  7.     }

Tadavía no lo subí a github, xq ví que tengo problemas en el remove, que si borro 3 me borra 4, si borro 1 me borra 2, en fin.

Espero sus respuestas y saludos.
  #54 (permalink)  
Antiguo 16/05/2017, 22:17
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Acabo de subir el código a github: https://github.com/detectivejd/HassM.../hashmapsimple

El problema está en si elimino entradas 1 y 3 funciona pero la 6 no debido a que la función hash de esa clave no está en el índice pero al eliminar el elemento y reemplazar por el último se me hizo díficil.
¿Qué voy a hacer ahora?

Espero sus respuestas y saludos.
  #55 (permalink)  
Antiguo 18/05/2017, 19:54
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Buenas a todos, logré resolver otros pequeños detalles pero el problema antes dicho no, esto es lo que pasa:

cuando borro la clave 1, me queda así:

null
6 => Denisse
2 => Tommy
3 => Franco
4 => Manuela
5 => Miguel
null
null

luego borro la clave 3, me queda así:

null
6 => Denisse
2 => Tommy
5 => Miguel
4 => Manuela
null
null
null

pero cuando quiero borrar la clave 6, no la borra, además de momento lo que hago es cambiar la posición del elemento a borrar por el último y luego al último le pongo null, la función hash me crea según la clave por ende me da índice 6 el que está en rojo:

null
6 => Denisse
2 => Tommy
5 => Miguel
4 => Manuela
null
null
null

viendo ese problema lo tengo tanto en el remove cómo en el get probablemente, pero si sólo le pongo null a la posición detectada por la función hash andaría pero tendría que rever mis iterator.

Subí a github: https://github.com/detectivejd/HassM.../hashmapsimple

MyMap.java:
línea 124 -> función hash
línea 208 -> remove

DownTest.java:
línea 55 -> test de la falla

Espero sus respuestas y saludos.
  #56 (permalink)  
Antiguo 21/05/2017, 22:31
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola a todos, viendo en la situación en la que estoy y la actual poca cooperación, me estuve planteando las siguientes opciones para salir de este lío:

1. Hacer que las búsquedas sean secuenciales pero pierden la esencia del hashing.
2. En el constructor de Entry poner el hash generado (idea más absurda que se me pudo ocurrir).

Si tienen otra opción digan por favor porque no me doy cuenta de cómo resolverlo.

Espero sus respuestas y saludos.
  #57 (permalink)  
Antiguo 23/05/2017, 21:45
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola a todos, la verdad que pude solucionar el problema, y las 2 ideas que se me ocurrieron ninguna fue, sino cambiar casi todo mi código por nodos, Gracias a Dios que se me ocurrió eso, aún me dan esto en los test:

java.lang.NullPointerException
at hashmapsimple.UpTest.probando_insercion(UpTest.jav a:97)
at hashmapsimple.UpTest.test(UpTest.java:107)
at hashmapsimple.Cuerpo.main(Cuerpo.java:8)
java.lang.Exception
at hashmapsimple.Test.comprobar_que(Test.java:6)
at hashmapsimple.GetTest.probando_busqueda_vacia(GetT est.java:39)
at hashmapsimple.GetTest.test(GetTest.java:49)
at hashmapsimple.Cuerpo.main(Cuerpo.java:10)
java.lang.NullPointerException
at hashmapsimple.DownTest.probando_borrado(DownTest.j ava:47)
at hashmapsimple.DownTest.test(DownTest.java:56)
at hashmapsimple.Cuerpo.main(Cuerpo.java:16)

Pero tendré que ver eso, CalgaryCorpus no sé si era eso a lo que te referías al cambiar la implementación del get, pero lo hice jeje.

Sí ven que hay algo que arreglar, avísenme por favor ya que puede haber un detalle que haya olvidado.

https://github.com/detectivejd/HassM.../hashmapsimple

Espero sus respuestas y Saludos.
  #58 (permalink)  
Antiguo 24/05/2017, 20:37
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Buenas a todos, les tengo que decir que acabo de tener los test y andan todos, ahora están estables:

https://github.com/detectivejd/HassM.../hashmapsimple

Si creen que hay un test que debería agregar o alguno innecesario, avísenme por favor.

En vista de esto creo que es hora de empezar a implementar el HashSet, sólo que tengo la pregunta de: ¿Que interface usar Collection o Set?

espero sus respuestas y saludos.
  #59 (permalink)  
Antiguo 26/05/2017, 19:53
 
Fecha de Ingreso: junio-2008
Ubicación: Seattle, USA
Mensajes: 733
Antigüedad: 15 años, 10 meses
Puntos: 61
Respuesta: Implementar TablaHash

Lo que tienes que detallar es que cosa estaba mal que antes los tests no andaban y ahora si. Es que los tests estaban mal escritos? es que la implementacion estaba mal?
que es lo que cambio? Es un poco pesado para el lector ocasional visitar un monton de codigo que no funciona, varias veces, como ha sucedido con este post.

Que es lo que aprendiste? Si logras compartir como fue tu implementacion, con que problemas te encontraste, que tests hiciste y como los superaste, este post servira de ayuda a quien lo ha seguido. Sino, creo que solo te servira' a ti, y la idea del foro es mas altruista que egoista, asi lo veo yo.
__________________
Visita mi perfil en LinkedIn
  #60 (permalink)  
Antiguo 27/05/2017, 21:23
Avatar de detective_jd  
Fecha de Ingreso: abril-2011
Ubicación: Salto
Mensajes: 437
Antigüedad: 13 años
Puntos: 6
Respuesta: Implementar TablaHash

Hola <b>CalgaryCorpus</b> me alegra que vuelvas a escribirme pensaba que estabas molesto conmigo por mis tonterías, hay varias cosas por decir:

Cita:
Lo que tienes que detallar es que cosa estaba mal que antes los tests no andaban y ahora si. Es que los tests estaban mal escritos? es que la implementacion estaba mal?
que es lo que cambio?
Verás lo que estaba mal era el cómo estaba encarado el código, al darle uso a los nodos cambiar casi toda su implementación se solucionó, con respecto a los test de UpTest y DownTest estaban mal encarados por el sólo chequeban si eran distintos de null cosa que si alguno era nulo, daba error Exception o NullPointerException, pasaba también mi ignorancia por poner mensajes que para los test no eran necesarios....

Cita:
Que es lo que aprendiste?
Sabía que los hashing eran estructuras de datos muy buenas para las búsquedas pero malas para las ordenaciones (al no ser que uses TreeMap), pero no sabía lo dependiente que eran de una fórmula de matemáticas (hash function) para la mayoría de sus funcionalidades, también que el uso de los nodos no sólo se límitan a los variados tipos de listas que existan también para los Map, también que no es lo mismo una implementación que hacer pruebas para garantizar que óptimos sean las funcionalidades de lo que
haces (en este caso el HashMap).

Cita:
Si logras compartir como fue tu implementacion con que problemas te encontraste, que tests hiciste y como los superaste, este post servira de ayuda a quien lo ha seguido. Sino, creo que solo te servira' a ti, y la idea del foro es mas altruista que egoista, asi lo veo yo.
De egoísmo nada, soy consciente que gran parte de lo hecho (48%) fue gracias a tu ayuda, eso sí que no soy alguien muy expresivo o muy comunicativo.
Me encontré con problemas de inexperiencia en los test, cómo también la dependencia de la función hash en la estructura, además de tonterías mías.
Los test que hicimos porque algunos fueron ideas tuyas, fueron cosas que a mí no se me hubieran ocurrido, además de que pensar en algo específico y no ver
todas las posibilidades de error, la indecisión de si usar nodos o a la vieja escuela fue otro problema grande y mis idas y vueltas.

El código lo pongo por si alguien lo quiere y claro también por si debería ir alguna prueba más que no haya tenido en cuenta:

https://github.com/detectivejd/HassM.../hashmapsimple

Por otro lado subí el código del HashSet casero que digamos la verdad, delega casi todo de hashmap, aunque tengo mis dudas:

https://github.com/detectivejd/HashS.../hashsetsimple

Con respecto a las pruebas estoy flojo porque no se me ocurre que más probar para el HashSet.
Mis dudas están con los métodos extras como containsAll que verifica si el set tiene todos los elementos de una coleccion, si no tiene uno devuelve falso.
el retainAll que conserva los elementos comúnes pero borra los otros y el removeAll borra todos los elementos de una colección, y la pregunta es:
¿para que los quiero? ¿porque las interfaces List y Set los tienen? ¿no era más fácil que las estructuras list y set no implementaran Collection? xq tiene las mismas
firmas Collection, además parece que el que creo parte del lenguaje tenía fascinación por las matemáticas digo por lo de conjuntos, intersecciones y demás.

Con respecto a errores me dice esto:

java.lang.Exception
at hashsetsimple.Test.comprobar_que(Test.java:6)
at hashsetsimple.ConstructorTest.creando_set_con_capa cidad_de_dos_elementos(ConstructorTest.java:25)
at hashsetsimple.ConstructorTest.test(ConstructorTest .java:70)
at hashsetsimple.Cuerpo.main(Cuerpo.java:7)

Lo más curioso es que en vez de guardarme 7 elementos me guarda 6, no quiero pensar que el error esta en la función hash, no sé que se te ocurre xq lo demás no da error alguno.

Espero sus respuestas y saludos.

PD: En un tema: ¿se pueden borrar mensajes?

Etiquetas: entrada, implementar
Atención: Estás leyendo un tema que no tiene actividad desde hace más de 6 MESES, te recomendamos abrir un Nuevo tema en lugar de responder al actual.
Respuesta




La zona horaria es GMT -6. Ahora son las 09:32.