{"id":23701172,"url":"https://github.com/gitfrandu4/kata2","last_synced_at":"2026-01-29T10:30:15.845Z","repository":{"id":211625168,"uuid":"216957491","full_name":"gitfrandu4/Kata2","owner":"gitfrandu4","description":"Histograma","archived":false,"fork":false,"pushed_at":"2020-01-16T00:25:03.000Z","size":74,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2024-12-30T09:32:45.986Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"Java","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gitfrandu4.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null}},"created_at":"2019-10-23T03:10:47.000Z","updated_at":"2020-01-16T00:25:05.000Z","dependencies_parsed_at":"2023-12-09T19:52:43.865Z","dependency_job_id":null,"html_url":"https://github.com/gitfrandu4/Kata2","commit_stats":null,"previous_names":["gitfrandu4/kata2"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gitfrandu4%2FKata2","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gitfrandu4%2FKata2/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gitfrandu4%2FKata2/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gitfrandu4%2FKata2/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gitfrandu4","download_url":"https://codeload.github.com/gitfrandu4/Kata2/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":239776638,"owners_count":19695146,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-12-30T09:32:27.880Z","updated_at":"2026-01-29T10:30:15.784Z","avatar_url":"https://github.com/gitfrandu4.png","language":"Java","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Kata2\n## Histograma\n\n**Objetivo**\n- Dado un array que se rellenará de valores enteros realizar una aplicación de consola para el cálculo del histograma, es decir la frecuencia de cada valor en ese array\n\n## Introducción\nHay determinadas clases que manipulan objetos (ArrayList, HashMap, ...).\n\nPara poder utilizar tipos primitivos con estas clases, Java provee las llamadas **clases envolventes**, también llamadas clases contenedoras o **Wrappers** (Integer, Double, etc.). Estas clases proporcionan métodos que permiten manipular el tipo de dato primitivo como si fuese un objeto. \n\nLas conversiones entre los tipos primitivos y sus clases envolventes (y viceversa) son automáticas. No es necesario hacer un casting. Para realizarlas Java utiliza el **Autoboxing**.\n\nA lo largo de las versiones de esta Kata2 usaremos un mapa (Array Asociativo) y lo implementaremos como *HashMap*. Inicialmente, tanto la clave como los valores podrán ser objetos de tipo entero (Integer). \n\nAdemás de los métodos `put()` y `get()`también se tienen estos:\n* `containsKey(Object Key)` =\u003e comprueba si el mapa contiene la clave *Key*.\n* `keySet()` =\u003e obtiene el conjunto de claves del mapa.\n\n## Iteración sobre mapas\nHay varias formas de iterar sobre un Mapa en Java. Vamos a repasar los métodos más comunes y revisar sus ventajas y desventajas.\n\nDado que todos los mapas en Java implementan la interfaz de Mapa, las siguientes técnicas funcionarán para cualquier implementación de un mapa (HashMap, TreeMap, LinkedHashMap, Hastable, etc.)\n\n### Método nº1. Iteración sobre las entradas utilizando un bucle *For-Each*\nEste es el método más común y es preferible en la mayoría de los casos. Debería usarse si se necesita en cada iteración tanto las claves como los valores del mapa. \n\n```java\nMap\u003cInteger, Integer\u003e map = new HashMap\u003cInteger, Integer\u003e();\nfor (Map.Entry\u003cInteger, Integer\u003e entry : map.entrySet()) {\n    System.out.println(\"Key = \" + entry.getKey() + \", Value = \" + entry.getValue());\n}\n```\n\nEste tipo de bucle lanzará un *NullPointerException* si se intenta iterar sobre un mapa que es nulo, por lo que antes de iterar siempre se debería verificar las referencias nulas. \n\n### Método nº2. Iteración sobre claves o valores utilizando un bucle *For-Each*\nSi solo se necesita claves o valores del mapa, se puede iterar sobre `keySet` o `values` en lugar de `entrySet`.\n\n```java\nMap\u003cInteger, Integer\u003e map = new HashMap\u003cInteger, Integer\u003e();\n//iterar solo sobre claves\nfor (Integer key : map.keySet()){\n    System.out.println(\"Key = \" + key);\n}\n\n//iterar solo sobre valores\nfor (Integer value : map.value()) {\n    System.out.println(\"Value = \" + value);\n}\n```\n\nEste método proporciona una ligera ventaja de rendimiento sobre la iteración `keySet` (aproximadamente un 10% más rápido) y es más limpio. \n\n### Método nº3. Iteración usando *Iterator*\n#### Opción a): usando *Generics*\n```java\nMap\u003cInteger, Integer\u003e map = new HashMap\u003cInteger, Integer\u003e();\nIterator\u003cMap.Entry\u003cInteger, Integer\u003e\u003e entries = map.entrySet().iterator();\nwhile (entries.hashNext()) {\n    Map.Entry\u003cInteger, Integer\u003e entry = entries.next();\n    System.out.println(\"Key = \" + entry.getKey() \" + \", Value = \" + entry.getValue());\n}\n```\n#### Opción b): sin usar *Generics*\n```java\nMap map = new HashMap();\nIterator entries = map.entrySet().iterator();\nwhile (entries.hashNext()) {\n    Map.Entry entry = (Map.Entry) entries.next();\n    Integer key = (Integer) entry.getKey();\n    Integer value = (Integer) entry.getValue();\n    System.out.println(\"Key = \" + key + \", Value = \" + value);\n}\n```\nTambién se puede usar la misma técnica para iterar sobre `keySet` o `values`.\n\nEste método puede parecer redundante pero tiene sus propias ventajas:\n1) Es la única forma de iterar sobre un mapa en versiones anteriores de Java y\n2) Es el único método que permite eliminar entradas del mapa durante la iteración llamando a `iterator.remove()`. Si se intenta hacer esto durante la iteración *For-Each* se obtendrá *\"resultados impredecibles*\" según javadoc. \n\nDesde el punto de vista del rendimiento, este método es igual a *For-Each*.\n\n### Método nº4. Iteración sobre claves y búsqueda de valores (ineficaz).\n\n```java\nMap\u003cInteger, Integer\u003e map = new HashMap\u003cInteger, Integer\u003e();\nfor (Integer key : map.keySet()) {\n    Integer value = map.get(key);\n    System.out.println(\"Key = \" + key + \", Value = \" + value);\n}\n```\n\nEsto podría parecer una alternativa más limpia para el método nº1 pero en la práctica es bastante lento e ineficaz ya que obtener valores con una clave puede consumir mucho tiempo. Ese método debe ser evitado en lo posible. \n\n### Conclusión\nSi solo necesita claves o valores del mapa, usa el método nº2. Si está atascado con una verión anterior de Java (menor de Java 5) o planea eliminar entradas durante la iteración, debe usar el método nº3. De lo contrario, usar el método nº1. \n\n## Atajos en NETBEANS para bucles for\n![](https://github.com/gitfrandu4/Kata2/blob/master/images/forShortcuts.png \"\")\n\n## Recordatorio\n\n### Operador ternario\nLa estrucura genérica de operador condicional ternario es:\n```\n    resultado = condición ? Valor1 : Valor2;\n```\nDonde la variable `resultado` recibirá `valor1` en el caso de que la `condición` sea verdadera o bien el `valor2` en el caso de que la `condición` sea falsa. \n\nPor ejemplo, si queremos calcular el mayor de dos números tendremos el siguiente código: `mayor = x\u003ey ? x : y;`\n\n### Clases y tipos genéricos en Java\nEn Java, cuando definimos una nueva clase, **debemos conocer el tipo de dato** con el que trabajaremos. \n\nSi queremos realizar una operación especíica dentro de esta nueva clase, sea cual sea el tipo de datos que va a recibir, podemos hacer uso de los tipos genéricos. Este tipo genérico asumirá el tipo de dato que realmente le pasaremos a la clase. \n\nEn Java se especifica que una **clase es de tipo genérico** poniendo `\u003cT\u003e` justo detrás del nombre de la clase:\n```\npublic class NombreClase\u003cT\u003e {\n    ...\n}\n``` \n## Referencias \n* http://puntocomnoesunlenguaje.blogspot.com.es/2013/02/java-clases-envolventes.html\n* https://es.stackoverflow.com/questions/54419/diferencia-entre-int-einteger\n* https://www.baeldung.com/java-loops\n* http://www.sergiy.ca/how-to-iterate-over-a-map-in-java/\n* http://lineadecodigo.com/java/el-operador-ternario-en-java/\n* https://picodotdev.github.io/blog-bitix/2016/04/tutorial-sobre-los-tipos-genericos-de-java/\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgitfrandu4%2Fkata2","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgitfrandu4%2Fkata2","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgitfrandu4%2Fkata2/lists"}