如果线程死亡,我该如何重新生成线程

时间:2013-12-12 22:03:16

标签: java multithreading

我有多个类型的多个线程(不同的类)。我希望万一他们中的一个抛出异常并死于被另一个新线程替换。我知道连接线程函数但是我将如何为5种不同类型的线程实现它们,例如在类型1线程模具被立即替换而不必等待类型2首先死亡的情况下。

这是一些示例伪代码。

class1 implements runnable{
  void run(){
     try{
       while(true){
         repeat task
        }
     } catch(Exception e){
      log error
     }
  }
}


class2 implements runnable{
  void run(){
     try{
       while(true){
         repeat task
        }
     } catch(Exception e){
      log error
     }
  }
}


class3 implements runnable{
  void run(){
     try{
       while(true){
         repeat task
        }
     } catch(Exception e){
      log error
     }
  }
}

public main(){

 // start all threads .start()
}

2 个答案:

答案 0 :(得分:3)

  

我希望万一其中一个抛出一个异常并死掉另一个新线程。

我不太明白为什么你不能这样做:

public void run() {
   // only quit the loop if the thread is interrupted
   while (!Thread.currentThread().isInterrupted()) {
      try {
         // do some stuff that might throw
         repeat task;
      } catch (Exception e) {
         // recover from the throw here but then continue running
      }
   }
}

为什么需要重新启动新线程?仅仅因为任务抛出异常并不意味着它在某种程度上是腐败的,它需要一个新的才能正常工作。如果您尝试捕获所有例外(包括RuntimeException),则catch (Exception e)会执行此操作。如果你想非常小心,你甚至可以抓住Throwable,以防有Error被生成 - 这是相对罕见的。

如果您实际上有多个任务(或者实际上在任何时候处理线程),您应该考虑使用ExecutorService类。请参阅Java tutorial

// create a thread pool with 10 workers
ExecutorService threadPool = Executors.newFixedThreadPool(10);
// or you can create an open-ended thread pool
// ExecutorService threadPool = Executors.newCachedThreadPool();
// define your jobs somehow
threadPool.submit(new Class1());
threadPool.submit(new Class2());
...
// once we have submitted all jobs to the thread pool, it should be shutdown
threadPool.shutdown();

因此,不是让一个线程执行多个任务,而是启动一个线程池,它会根据需要启动线程来完成一堆任务。如果任务失败,您可以确定向池中提交另一个任务,尽管这有点奇怪。

如果您想等待所有任务完成,请使用:

threadPool.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);

答案 1 :(得分:1)

      boolean shouldStop() {
        // it's a good idea to think about how/when to stop ;)
        return false;
      }
      void runThreadGivenType(final Runnable taskToRun) {
        new Thread() {
          @Override
          public void run() {
            try {
              taskToRun.run();
            } finally {
              if (!shouldStop()) {
                runThreadGivenType(taskToRun);
              }
            }
          }
        }.start();
      }

      public void main(String[] args) throws Exception {
        runThreadGivenType(new Runnable() { public void run() { System.out.println("I'm almost immortal thread!"); throw new RuntimeException(); } });
        TimeUnit.SECONDS.sleep(10);
      }

并且考虑执行程序来管理线程池也是一个好主意。普通的,[un / hand]管理的线程不是最好的做法;)