在使用java类启动线程列表后,如何识别并重新启动已终止的线程?

在使用java类启动线程列表后,如何识别并重新启动已终止的线程?,java,multithreading,Java,Multithreading,我已经在我的类中启动了20个线程,每个线程将在一个循环中运行以完成一些事情 for(int i=1;i<=20;i++) { MyThread mt = new MyThread(i); Thread t = new Thread(mt); t.start(); } 现在我想监视每个线程,如果其中任何线程停止,我想用相应的threadId启动一个新线程。我该怎么做?请帮助我。如果要测试线程,请在数组中保留线程列表: MyThre

我已经在我的类中启动了20个线程,每个线程将在一个循环中运行以完成一些事情

for(int i=1;i<=20;i++) {
    MyThread mt = new MyThread(i);                  
    Thread t = new Thread(mt);
    t.start();
}

现在我想监视每个线程,如果其中任何线程停止,我想用相应的threadId启动一个新线程。我该怎么做?请帮助我。

如果要测试线程,请在数组中保留线程列表:

MyThread[] mt = new MyThread[20];
...
mt[i] = ...

现在,您可以使用thread类中的方法查询每个线程,例如:isAlive()

我将从Thread类的可能状态开始。有6种可能的状态:

新建:尚未启动的线程处于此状态

RUNNABLE:在Java虚拟机中执行的线程位于 国家

阻塞:在等待监视器锁定时被阻塞的线程处于锁定状态 这个州

等待:无限期地等待另一个线程启动的线程 在此状态下执行特定操作

TIMED_WAITING:等待另一个线程执行的线程 指定等待时间内的操作处于此状态

已终止:已退出的线程处于此状态

正如您所说的“已终止”的线程是那些处于终止状态的线程。有两个主要原因会导致终止状态

  • A) run()方法在完成工作后正常退出
  • B) 发生异常并结束run()方法
如果您希望线程“从不”进入终止模式,那么您应该A)有一个无限循环B)捕获所有异常。但这不完全是你的问题。如何监视线程的状态

关键是方法

public Thread.State getState()

返回此线程的状态。此方法设计用于监视系统状态,而不是用于同步控制

您可以使用以下3个类执行任何操作:

App.java

package com.what.ever;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.TimeUnit;

public class App {

    private static int MONITORING_FREQUENCY = 5;
    private static int NUMBER_OF_TASKS = 3;

    public static void main(String[] args) {
        List<ThreadMonitor> threadMonitors = initThreadMonitors();

        threadMonitors.forEach(m -> m.printState());
        threadMonitors.forEach(m -> m.startThread());

        ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);
        scheduler.scheduleAtFixedRate(() -> threadMonitors.forEach(m -> m.restartIfTerminated()), MONITORING_FREQUENCY, MONITORING_FREQUENCY, TimeUnit.SECONDS);
    }

    private static List<ThreadMonitor> initThreadMonitors() {
        List<ThreadMonitor> threadMonitors = new ArrayList<>();

        for (int i = 1; i <= NUMBER_OF_TASKS; i++) {
            DummyRunnable runnable = new DummyRunnable(i);
            ThreadMonitor threadMonitor = new ThreadMonitor(runnable);
            threadMonitors.add(threadMonitor);
        }

        return threadMonitors;
    }
}
DummyRunnable.java

package com.what.ever;

public class DummyRunnable implements Runnable {

    private int id;

    public DummyRunnable(int id) {
        this.id = id;
    }

    public void run() {
        System.out.println("Runnable " + id + " started in thread: " + Thread.currentThread());
        dummyWork();
        System.out.println("Runnable " + id + " done");
    }

    private void dummyWork() {
        int sleep = 10000;
        if (id == 3) {
            sleep = 1000;
        }
        try {
            Thread.sleep(sleep);
        } catch (Exception e) {
            System.out.print(e);
        }
    }
}
给你。如果你对这个例子有任何疑问,就问吧

小警告:
注意监控频率,它会对性能产生巨大影响。不要试图用它来执行实时应用程序。

确保线程不会停止怎么样
尝试
/
捕获
抛出的任何
异常
。本文使用自定义侦听器在线程停止时获得通知:@Andy Turner Java代码异常是线程停止的唯一方法吗?我们可以从主类监视线程并检查它们是否处于活动状态吗?@user3608212还有其他方法可以停止它们;但是这些方法通常都是非常激烈的,所以你可能无论如何都想放弃。请不要担心你无论如何都无法重新启动线程,所以你唯一能做的就是捕获异常
package com.what.ever;

public class ThreadMonitor {

    private Thread thread;
    private DummyRunnable runnable;

    public ThreadMonitor( DummyRunnable runnable) {
        this.runnable = runnable;
        this.thread = new Thread(runnable);
    }

    public boolean startThread() {
        boolean isStarCalled = false;
        if(Thread.State.NEW.equals(thread.getState())) {
            thread.start();
            isStarCalled = true;
        }
        return isStarCalled;
    }

    public void printState() {
        System.out.println( thread.toString() + " is in state : " + thread.getState());
    }

    public void restartIfTerminated() {
        printState();
        if(Thread.State.TERMINATED.equals(thread.getState())) {
            thread = new Thread(runnable);
            thread.start();
        }
    }
}
package com.what.ever;

public class DummyRunnable implements Runnable {

    private int id;

    public DummyRunnable(int id) {
        this.id = id;
    }

    public void run() {
        System.out.println("Runnable " + id + " started in thread: " + Thread.currentThread());
        dummyWork();
        System.out.println("Runnable " + id + " done");
    }

    private void dummyWork() {
        int sleep = 10000;
        if (id == 3) {
            sleep = 1000;
        }
        try {
            Thread.sleep(sleep);
        } catch (Exception e) {
            System.out.print(e);
        }
    }
}