Después de años rellenando formularios y esperando, por fin has conseguido tu licencia bancaria. Esto significa que ahora puedes abrir oficialmente tu propio banco, ¡hurra!
Tu primera prioridad es poner en marcha los sistemas informáticos. Después de un día de duro trabajo, ya puedes abrir y cerrar cuentas, además de gestionar ingresos y reintegros.
Como no tenías ganas de escribir tests, invitas a unos amigos para que te ayuden a probar el sistema. Sin embargo, a los cinco minutos, uno de tus amigos afirma que ha perdido dinero. Aunque confías en que tu código no tiene errores, empiezas a revisar los registros para investigar.
Ah, sí, justo como sospechabas, ¡tu amigo tiene la culpa! Compartió sus credenciales de prueba con otro amigo y, juntos, conspiraron para hacer ingresos y reintegros desde la misma cuenta en paralelo. ¿A quién se le ocurriría hacer algo así?
Mientras argumentas que es físicamente imposible que alguien acceda a su cuenta en paralelo, tu amigo te informa con suficiencia de que las normas bancarias exigen que lo soportes. Así que, sin soporte para la banca en paralelo, no hay señal de lanzamiento. Suspiras y te apuntas mentalmente que mañana te pondrás con ello. Esto retrasará tu fecha de lanzamiento al menos un día más, pero bueno...
Tu tarea consiste en implementar cuentas bancarias que admitan aperturas y cierres, retiradas e ingresos de dinero.
Como se puede acceder a las cuentas bancarias de muchas maneras distintas (internet, teléfonos móviles, cargos automáticos), tu software bancario debe permitir acceder a las cuentas de forma segura desde varios hilos o procesos en paralelo (la terminología depende de tu lenguaje de programación). Por ejemplo, puede haber muchos ingresos y retiradas ocurriendo en paralelo; debes asegurarte de que no haya condiciones de carrera entre el momento en que lees el saldo de la cuenta y aquel en que estableces el nuevo saldo.
Debe ser posible cerrar una cuenta; las operaciones sobre una cuenta cerrada deben fallar.
Este ejercicio introduce la concurrencia.
Para superar el último test, puede que te resulten útiles la palabra clave synchronized o los bloqueos.
Los problemas que surgen al ejecutar código de forma concurrente suelen ser intermitentes, porque dependen del orden en que se ejecuta el código. Por eso, el último test ejecuta muchos hilos varias veces para aumentar las posibilidades de detectar un bug. Esto significa que el test debería fallar si tu implementación no es segura para hilos, pero es posible que lo pase solo porque no hubo ningún intento de modificación concurrente. Es poco probable que esto ocurra varias veces seguidas, ya que el orden en que se ejecuta el código debería variar cada vez que ejecutas el test. Así que, si ejecutas el último test un par de veces y lo pasa siempre, puedes estar bastante seguro de que tu implementación es correcta.
Regístrate en Exercism para aprender y dominar Java con 26 conceptos158 ejercicios y mentoría humana real, todo gratis.