2012-08-30 20 views
8

He estudiado muchos tutoriales sobre hilos en Java pero no puedo encontrar mi respuesta.Ejecutar dos tareas independientes simultáneamente usando hilos

Mi pregunta es: ¿cómo ejecutar dos hilos independientes al mismo tiempo?

Mi caso es: Tengo dos tareas;

  1. guardar algunos datos a la base de datos
  2. enviar una notificación de inserción en un dispositivo móvil.

Dado que estas dos tareas son independientes, quiero ejecutarlas simultáneamente.

Intenté utilizar un grupo de subprocesos con dos subprocesos, pero el problema es que las tareas de la base de datos finalizan rápidamente, pero lleva un tiempo enviar una notificación de inserción.

En consecuencia, cuando una tarea finaliza mientras que la otra todavía está pendiente, arroja una excepción.

También no hay ningún problema en mi código porque funciona bien sin usar hilos.

Gracias de antemano

+2

* arroja una excepción * podría ser útil publicar la excepción aquí – Robin

+1

¿Están relacionadas las tareas de todos modos? Es decir, ¿desea enviar una notificación DESPUÉS de que se hayan guardado los datos? ¿O solo quieres poner en cola un montón de tareas al azar en una cola? – MadProgrammer

+0

@MadProgrammer gracias por su rápida respuesta.base de datos ambas tareas son independientes entre sí. por lo tanto, no importa si los datos se guardan primero o si se envía primero una notificación de inserción –

Respuesta

25
new Thread(new Runnable() { 
    public void run() { 
     System.out.println("Look ma, no hands"); 
    } 
}).start(); 

new Thread(new Runnable() { 
    public void run() { 
     System.out.println("Look at me, look at me..."); 
    } 
}).start(); 

funciona bien ...

preferiría el uso de un ExecutorService personalmente.

actualiza con ExecutorService ejemplo

Así que escribió este ejemplo muy rápido ...

Básicamente se utiliza un ExecutorService para ejecutar un par de tareas sencillas. En su forma actual, tanto tarea se ejecutará en paralelo entre sí (al mismo tiempo)

public static void main(String[] args) throws InterruptedException { 
    ExecutorService service = Executors.newFixedThreadPool(2); 
    service.submit(new PathScanner()); 
    service.submit(new Counter()); 

    service.shutdown(); 
    service.awaitTermination(1, TimeUnit.DAYS); 

    System.exit(0); 
} 

public static class PathScanner implements Callable<Object> { 

    @Override 
    public Object call() throws Exception { 
     scan(new File("C:/"), 0); 
     return null; 
    } 

    protected void scan(File path, int deepth) { 
     if (deepth < 15) { 
      System.out.println("Scanning " + path + " at a deepth of " + deepth); 

      File[] files = path.listFiles(); 
      for (File file : files) { 
       if (file.isDirectory()) { 
        scan(file, ++deepth); 
       } 
      } 
     } 
    } 
} 

public static class Counter implements Callable<Object> { 

    @Override 
    public Object call() throws Exception { 
     for (int index = 0; index < 1000; index++) { 
      Thread.sleep(1); 
      System.out.println(index); 
     } 
     return null; 
    } 
} 

Run que ...

Ahora cambiar ExecutorService service = Executors.newFixedThreadPool(2);-ExecutorService service = Executors.newFixedThreadPool(1); y ejecutarlo de nuevo. ¿Viste la diferencia?

Esta es la forma de controlar el número de subprocesos simultáneos que el ejecutor puede usar mientras procesa su cola.

Componga algunas tareas más y agréguelas a la cola para ver qué obtiene.

+2

+1 para el ejemplo rápido ... – John

+0

¡gracias por su rápida respuesta y por ejemplo! respuesta aceptada! :-) –

+0

En su primer ejemplo, ¿cómo imprimo la identificación del hilo? –

0

Estaba teniendo un caso de uso para buscar archivos en varias carpetas utilizando multihebra. Como entrada, solo tenía la ruta del directorio raíz y puede haber cualquier cantidad de directorios secundarios. Suposición: el archivo siempre estará disponible solo en uno de los directorios secundarios.

import java.io.File; 
import java.io.FileFilter; 
import java.util.concurrent.ExecutorService; 
import java.util.concurrent.Executors; 

public class SearchFile implements Runnable { 

    private String dirPath = null; 

    public SearchFile() { 

    } 

    public SearchFile(String dirPath) { 
     this.dirPath = dirPath; 
    } 

    public static void main(String[] args) { 
     long startTime = System.currentTimeMillis(); 
     File dir = new File("D://"); 
     checkRootDirectory(dir); 
     long endTime = System.currentTimeMillis(); 
     System.out.println("Time taken: "+(endTime - startTime) + "ms"); 
    } 

    private static void checkRootDirectory(File root) { 
     File[] list = root.listFiles(new FileFilter() { 

      @Override 
      public boolean accept(File pathname) { 
       return pathname.isDirectory() && !pathname.isHidden(); 
      } 
     }); 

     ExecutorService service = Executors.newFixedThreadPool(list.length); 
     for (File directories : list) { 
      String dirPath = directories.getAbsolutePath(); 
      Thread thread = new Thread(new SearchFile(dirPath)); 
      service.execute(thread); 
     } 
     service.shutdown(); 
     while(!service.isTerminated()) { 

     } 
    } 

    @Override 
    public void run() { 
     checkEachDirectory(new File(dirPath), "Temp.txt"); 
    } 

    private void checkEachDirectory(File root, String fileName) { 
     File[] list = root.listFiles(); 
     if (null != list) { 
      for (File dir : list) { 
       if (dir.isDirectory()) { 
        checkEachDirectory(dir, fileName); 
       } else if (fileName.equalsIgnoreCase(dir.getName())) { 
        System.out.println(
          "Thread name: " + Thread.currentThread().getName() + " Founded @" + dir.getAbsolutePath()); 
       } 
      } 
     } 
    } 
} 
Cuestiones relacionadas