Todos conocemos la clase Object y los métodos principales que posee como equals y hashcode. Sin embargo a mucha gente le cuesta entender para que sirven java wait notify,dos métodos que pertenecen a la clase Object y estan relacionados con programación concurrente, vamos a abordarlo. Para ello vamos a crearnos dos clases sencillas (Bolsa y Producto) donde una Bolsa contiene varios Productos.
Vamos a ver su código:
package com.arquitecturajava; import java.util.ArrayList; public class Bolsa { private ArrayList<Producto> listaProductos = new ArrayList<Producto>(); public void addProducto(Producto producto) { if (!estaLlena()) listaProductos.add(producto); } public ArrayList<Producto> getListaProductos() { return listaProductos; } public int getSize() { return listaProductos.size(); } public boolean estaLlena() { return listaProductos.size() >= 5; } }
package com.arquitecturajava; public class Producto { private String nombre; public String getNombre() { return nombre; } public void setNombre(String nombre) { this.nombre = nombre; } }
Lo único que tiene de peculiar la bolsa que hemos creado es que no permite que se le añadan más de 5 elementos. Ahora vamos a construir dos Threads un primer Thread que va poco a poco llenando la bolsa (thread main) y otro Thread que cuando la bolsa este llena la envía. Vamos a ver el Thread que envía la bolsa:
package com.arquitecturajava; public class HiloEnvio extends Thread { private Bolsa bolsa; public HiloEnvio(Bolsa bolsa) { super(); this.bolsa = bolsa; } @Override public void run() { if (bolsa.estaLlena() != true) { try { synchronized (bolsa) { bolsa.wait(); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } System.out.println("Enviando la bolsa con "+ bolsa.getSize()+"elementos"); } } public Bolsa getBolsa() { return bolsa; } public void setBolsa(Bolsa bolsa) { this.bolsa = bolsa; } }
Este Hilo se encarga de sacarnos por pantalla el mensaje de “Enviando la bolsa con 5 elementos” . Para ello recibe la Bolsa como parámetro y chequea que esta llena. Usa un bloque de código sincronizado (syncronized) . Este bloque de código coordina el trabajo entre nuestros dos Threads y permite que un Thread llene la Bolsa y cuando este llena el otro Thread la envíe.
Lamentablemente ambos Threads deben de estar sincronizados ya que hasta que la bolsa no este llena no la podemos enviar. Para sincronizar el trabajo de los Threads usamos la pareja wait notify. De tal forma que nuestro primer HiloEnvio se pondrá a esperar(wait) hasta que la Bolsa este llena antes de enviarla. Para rellenar la bolsa usamos el Thread del programa principal que cada segundo añadirá un nuevo elemento a la lista.
package com.arquitecturajava; public class Principal { public static void main(String[] args) { Bolsa bolsa= new Bolsa(); HiloEnvio hilo= new HiloEnvio(bolsa); hilo.start(); for(int i=0;i<=10;i++) { Producto p= new Producto(); try { synchronized (bolsa) { Thread.sleep(1000); if (bolsa.estaLlena()) { bolsa.notify(); } } } catch (InterruptedException e) { e.printStackTrace(); } bolsa.addProducto(p); System.out.println(bolsa.getSize()); } } }
Como vemos el método main va añadiendo productos a la Bolsa y cuando esta llena notifica (notify) al otro Thread de que ya puede procesarlo saliendo del estado wait en el que se encuentra.
El uso de wait() y notify() es muy habitual en programación concurrente y son parte de la clase Object ya que lo que bloqueamos y sincronizamos es el acceso a cada uno de los objetos. Si ejecutamos el programa nos saldrá por consola el siguiente resultado:
En cuanto tenemos 5 elementos y la bolsa llena el Thread principal no puede añadir más pero ha notificado al otro Thread que en cuando pueda realice su trabajo que es enviar la bolsa.
[…] artículos relacionados : Java Executor Service y Threading ,Java wait notify y threads , JavaScript Promise y la programación […]
[…] Otros artículos relacionados : Java Collection Performance , Java Fluid Interface , Java Threads […]
cecilio buen dia… la consulta es sobre su libro arquitectura java solida.. estoy sigiuiendolo y me quede en una parte… llegado un momento en la JSP mostrar libro…. se le agrega un filtro para mostrar solo las categoras que el usuario quiera… mi pregunta es cuando se pulsa ese boton, se envia el parametro categoria del combo (select)… pero quien recibe esos datos… tengo que crear otra JSP… o es la misma JSP mostrarlibros la que se encarga de gestionar esos datos?……. gracias
como realizar un threads que verifique mi base de datos si algún producto se esta agotando y que me envié una notificación en java no se por donde empezar xD
Podrías usar un servicio de timer de EJB que cada x tiempo te consulte .. por ejemplo
Hola nuevamente Cecilio…. estoy siguiendo tu libro y me surgio otra doda…. esta ves no tiene que ver con los hilos de ejecucion pero no sabia donde hacer la consulta asi que postie aca….. yo venia siguiendo los ejemplos y me detuve en la parte en la cual… haciendo uso del principio dry creas una clase java que se encarga de gestionar las consultas sql de accion y seleccion para simplificar los codigos de las paginas JSP…… el problema es que yo creo un proyecto java, un paquete y la clase respectiva todo esto dentro de la aplicacion web…. pero… Read more »
Hola Cecilio, estaba aprendidendo java…y tenia algunas dudas con los subprocesos. vi tu explicacion y me aclaro un poco mis dudas pero igual me quedaron algunas. en el ejemplo que nos distes. en esta parte en particular public void run() { if (bolsa.estaLlena() != true) { try { synchronized (bolsa) { bolsa.wait(); } } catch (InterruptedException e) { // TODO Auto-generated catch block e.printStackTrace(); } cuando llamamos a Start() y comienza la ejecucion del hiilo…… luego … si la bolsa aun no esta llena suspendemos el subproceso… llamando al metodo wait de la clase Thread… mi duda es… quien es… Read more »
Cualquier objeto puede llamar al método wait() y suspenderá la ejecución el hilo actual que pasará a un estado de waiting. Una vez hecho esto solo se despertará tras un notify .
hay que tener en cuenta que wait y notify solo tienen efecto en un contexto sincronizado, tal como nos lo muestra él en su ejemplo
gracias Cecilio por tomarte el tiempo de responder.
de nada 🙂
Hola, Cecilio.
En primer lugar agradecerte el esfuerzo por mantener una “web” como esta. Es realmente muy útil.
Solo decirte, de manera constructiva y para darle más categoría si cabe a la página, que no tuviera tantas faltas gramaticales y ortográficas.
Saludos,
Javero
Me apunto las ideas gracias por los comentarios 🙂