Preparamos nuestra primera Code Kata

Las katas, en artes marciales, son una serie de movimientos predefinidos, que se entrenan y aprenden a base de repetirlos, y que sirven como método de práctica para entender las características del tipo de arte marcial del que se trate. Esta misma idea se llevó al concepto de la programación: A través de una serie de ejercicios preestablecidos y a base de práctica y repetición, permiten al que los practica aprender a programar en uno o varios lenguajes.

Desde el Aula de Software Libre estamos preparando una Code Kata para el próximo viernes 27 de febrero. Nos juntaremos en el Aula B1 del Edificio Ramón y Cajal a las 16 horas.

¿Cómo se plantean las katas?

Se proponen una serie de ejercicios, de diferente dificultad (baja, media, alta/muy alta). Que cada uno se atreva con lo que quiera. El ejercicio consiste en resolver el problema pero cumpliendo las siguientes reglas:

  • Las sesiones de «entrenamiento» deben durar entre 30 y 60 minutos, sin interrupciones. Debes estar tranquilo, así que aprovecha para apagar el móvil y alejarte durante un momento del Telegram y demás distracciones.
  • Como se trata de aprender a base de repetir, cada intento de resolver el problema se guarda. Es decir, si resuelves el problema, guardas esa versión y vuelves a empezar, esta vez intentando solucionar el problema de otra manera. Puedes (y debes) mirar el código que has hecho antes.
  • El objetivo no es encontrar la respuesta correcta, sino aprender a programar. Por eso mismo el lenguaje que escojas no es lo importante, sino la forma de programar. Usa el lenguaje con el que te sientas más cómodo, o aquel que querías aprender y no encontrabas cómo empezar a utilizarlo.

Estos ejercicios los resolvéis cuando queráis. El día en que quedemos, se irán presentando las soluciones que habéis tomado. El objetivo de esta parte es discutir la resolución del problema, de tal manera que los que tengan menos experiencia programando puedan ver como resuelven los que llevan más. Y los «veteranos», que posiblemente ya tienen una manera cerrada de pensar, puedan ver nuevas perspectivas de atacar problemas por parte de los más noveles.

IMPORTANTE: Seguro que las soluciones están en Internet, pero esto ni es un examen ni es un trabajo de clase ni nadie te obliga a asistir, ni se trata de quedar bien. Si copias las soluciones después no podrás explicarlas y no te va a servir de nada, además de hacernos perder a los demás el tiempo.

¿Qué pasa si no soy capaz de resolverlos?

Nada, lo importante es intentarlo aunque te equivoques. A programar se aprende programando. El día que quedemos, haberlo aunque sea intentando te ayudará a entender las propuestas de los demás y a mejorar.

Las pruebas

Los problemas deben pasar pruebas de unidad. Como no os puedo proporcionar pruebas para todos los lenguajes, vamos a usar una web que ya trae muchos problemas (y de la cual he seleccionado tres). Permite probar el código para ver si funciona en multitud de lenguajes (C, C++, Java, PHP, C#, Python2/3, Javascript, …).

La web se llama CodeEval. Permite el registro con Github, así que si no tenéis cuenta, es una buena oportunidad para crearos una y aprender a usar Git.

Los problemas seleccionados son:

PROBLEMA 1: FIZZ BUZZ (dificultad baja)

Ver enunciado del problema en Codeeval

Una serie de jugadores en corro, van diciendo números de forma consecutiva. Cuando un número es múltiplo de otro número X (por ejemplo 3), el jugador que tiene que decirlo pronuncia en su lugar FIZZ. Si, sin embargo, es múltiplo de otro número Y distinto de X (por ejemplo 5), pronuncia la palabra BUZZ. Si el número es divisible por ambos números dice FIZZ BUZZ.

El problema consiste en programar una aplicación que reciba como parámetro tres números, el valor X, el valor Y y un número N que indica hasta que valor se debe contar. Como salida devolverá los N primeros números naturales, pero sustituyendo los múltiplos de X por la letra F, los de Y por B y los de ambos por FB.

Ejemplo entrada: 2 7 15
Ejemplo salida: 1 F 3 F 5 F B F 9 F 11 F 13 FB 15

PROBLEMA 2: ROMAN AND ARABIC (dificultad media)

Ver enunciado del problema en Codeeval

Se nos presenta un número formados por pares AR, siendo A una cifra en sistema decimal y R en números romanos. El valor del par AR es A veces el valor de R. Ejemplo: 5V = 5 * 5 = 25. El valor del par se suma al del siguiente si R del primer par es mayor o igual al del siguiente o se resta en caso contrario.
Ejemplo: 3C4X = 3*100+4*10 = 340 ; 4X3C = - 4 * 10 + 3 * 100 = 260

Ejemplo entrada: 2I3I2X9V1X
Ejemplo salida: -16

PROBLEMA 3: CRACKING EGGS (dificultad alta)

Ver enunciado del problema en Codeeval

Este problema es más un problema matemático que de programación, pero se presenta por ser su resolución bastante curiosa (aunque difícil de ver). Sobre todo puede costar entenderlo, así que ampliamos la descripción con respecto a la oficial. La web solo da un caso de prueba, lo que añade más dificultad.

Tenemos un edificio de N plantas y una cesta de K huevos. No son huevos normales, sino que son capaces de aguantar una caída desde una altura desconocida de dicho edificio. Nuestro trabajo consiste en saber cuál es la planta más alta desde que podemos tirar un huevo sin romperlo en el peor de los casos, usando el menor número de intentos. En este problema es importante no confundir número de huevos con número de intentos. Si tiráramos un huevo desde la primera planta y no se rompiera, es un huevo que podemos volver a usar, pero sería ya un intento.

La aplicación recibe un fichero como parámetro que contiene una lista de valores separados por espacio. Cada línea representa en primer lugar el número de huevos y el número de plantas. Por cada línea se devuelve el número de intentos solicitado.

Ejemplo entrada: 2 100
Ejemplo salida: 14

El ejemplo anterior indica que si nos dan dos huevos y tenemos un edificio de 100 plantas, en la solución más desfavorable para nuestro algoritmo, el máximo número de intentos sería 14.

Para facilitar la resolución del problema, se presentan otros casos de prueba:

Entrada:
2 1000
3 1000
4 1000
Salida:
45
19
13