java concurrency timer while-loop swingworker

java - ¿Usa un temporizador para comenzar un SwingWorker?



concurrency timer (4)

¿Qué tan grande es el conjunto de datos que está recuperando? Si es bastante pequeño, separaría por completo la tarea de buscar / procesar y mostrar.

  1. Utilice algún tipo de memoria caché para contener el conjunto de datos procesados ​​más recientemente.
  2. Use un javax.swing.Timer para actualizar la GUI con los datos en caché.
  3. Use un java.util.Timer para obtener los datos de la base de datos, procesarlos y actualizar la memoria caché.
  4. Tenga cuidado con los problemas de sincronización entre las dos veces en su caché. No desea que su temporizador de oscilación agarre datos al mismo tiempo que el otro temporizador lo está actualizando.

La tarea que necesito realizar implica solicitar algunos datos de un servidor externo, realizar algunos procesos (bastante largos) en los datos y luego actualizar la GUI con los resultados del procesamiento. Debido a que el servidor puede no responder, la tarea es adecuada para un SwingWorker: el método doInBackground() obtiene los resultados, y luego el método hecho actualiza la GUI.

Necesito que esto suceda una vez cada pocos segundos. Sé que puedo usar un ciclo while y Thread.sleep, y crear un nuevo SwingWorker después de cada sueño. Pero todo lo que he leído frunce el ceño al usar bucles y dormir. Me gustaría utilizar un temporizador pero:

  • Usar un temporizador de oscilación parece contraproducente; ya que se ejecutan en el EDT, esencialmente no tengo ninguna razón para usar el método doInBackground de SwingWorker. Si el servidor no respondía, la GUI no respondería.

  • Usar un java.util.Timer parece un desperdicio: parece crear un hilo de fondo para TimerTask (), y como solo estoy creando un SwingWorker para hacer el trabajo real, básicamente estoy creando un hilo de fondo que crea otro hilo de fondo.

¿Alguien puede decirme cuál es la mejor solución? Me gustaría seguir con SwingWorker, ya que parece ideal para la tarea, pero me gustaría evitar el uso de un ciclo while si puedo evitarlo.

Gracias


No veo por qué no podrías usar un temporizador de oscilación para iniciar un Swing Worker. ¿Qué has intentado?


Puede usar un ScheduledExecutorService :

scheduleAtFixedRate(Runnable command, long initialDelay, long period, TimeUnit unit) // get a scheduled executor service with one thread ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1); // schedule the worker at an intervall of 5 seconds scheduler.scheduleAtFixedRate(myWorker, 0, 5, TimeUnit.SECONDS);


Creo que estás en el camino correcto con SwingWorker. Ahora necesita ver sus métodos de publicación y proceso. A medida que avanza su procesamiento, publica () un objeto del subproceso en segundo plano, luego se llama al método process () en el subproceso Swing (EDT) para que pueda actualizar la GUI.

De esta forma, no hay un montón de temporizadores y otros hilos para coordinar.

Los javadocs tienen un ejemplo sencillo con números primos: http://download.oracle.com/javase/6/docs/api/javax/swing/SwingWorker.html