通过线程名称杀死Java线程

时间:2019-12-12 17:33:27

标签: java multithreading

我有一个脚本,该脚本每15秒运行一次,并且每次都会创建一个新线程。有时该线程会卡住并阻塞程序的同步过程。现在,如果线程被卡住20个循环,我想杀死一个特定名称的进程。这是我的代码:

public void actionPerformed(ActionEvent e) {


        Date dNow = new Date( );
        SimpleDateFormat ft = new SimpleDateFormat ("dd-MM-yyyy HH:mm:ss");
        System.out.println(ft.format(dNow));

        ThreadGroup currentGroup = Thread.currentThread().getThreadGroup();
        int noThreads = currentGroup.activeCount();
        Thread[] lstThreads = new Thread[noThreads];
        currentGroup.enumerate(lstThreads);
        boolean loopthreadfound = false;
        for (int i = 0; i < noThreads; i++){
        try{    
        if (lstThreads[i].getName() == "loopthread"){loopthreadfound = true;}           
        }catch(Exception e1){System.out.println(e1);}
        }

        if (loopthreadfound == false){
            loopthreadcounter = 0;
            //Starten in nieuwe thread
            Thread loopthread = new Thread() {

            public void run() {

                try {
                    checkonoffline();
                    checkDBupdates();
                    } catch (JSONException | SQLException | IOException e1) {
                    System.out.println(e1);
                    }
            }

            };

            loopthread.setName("loopthread");
            loopthread.start();

        }else{

            loopthreadcounter++;
            System.out.println("Loopthread already running...   counter: " + loopthreadcounter);        

            if (loopthreadcounter > 20){

             // HERE I WANT TO KILL THE THREAD "loopthread "

            }
        }

}

2 个答案:

答案 0 :(得分:0)

通常,线程名称不是唯一的。如果要将StringThread关联在一起,并且该字符串标识了要停止的线程,请自己进行跟踪,而不要将其视为线程名称。

也就是说,创建一个Map<String, Thread>。稍后,您可以通过“名称”从映射中获取正确的线程,并将其终止。

请注意,stop()已过时。您应该找到杀死,中断或终止被阻止操作的正确方法。

答案 1 :(得分:0)

您无法杀死Java中的线程。

因此,让我们退后一步:您遇到了问题,并且认为:我知道!我会杀死线程...我该怎么做?

错误的策略。 “外部”(例如,不是从线程本身的代码内部进行)使线程结束的最常见方法是告诉线程进行自我清理。无论如何,那是...您在其中编写一些代码以便它发生的地方。

对于您的情况:大概有些I / O操作被卡住了。对于大多数I / O和大多数OS,您可以中断线程。这会导致IOException发生,从而“解贴”任何卡住的内容。我给你看一个例子。我将使用Thread.sleep而不是I / O op,因为Java规范保证了可中断性:

在线程的代码中:

public void run() {
    while (!Thread.interrupted()) {
        doExpensiveOp();
        try {
            // sleep a long time
            Thread.sleep(1000000);
        } catch (InterruptedException e) {
            return;
        }
    }
}

以及控制代码中的

Thread x = ... that thread.;
x.interrupt();

interrupt方法将“提高中断标志”,仅此而已。但是,许多Java核心库调用都与之交互。例如,如果定义为“ throw InterruptedException”的所有 ALL 方法在线程被中断时正在睡眠,则它们将立即退出,并且如果标志已启动并且您调用了这些方法之一,则不会这样做。根本不运行,它们立即退出该异常。我们还在while循环中检查标志的状态。因此,如果我们处于sleep()操作中,则如果您中断它,上述线程代码肯定会退出。如果线程当前处于其昂贵的操作部分中,则将发生以下三种情况之一:

  1. 此操作完全忽略它。当然有可能;只有声明为抛出InterruptedEx的方法才得到 GUARANTEED 的正确处理。至少在操作结束的那一刻,您的线程肯定会退出,因为睡眠调用会立即引发InterruptedEx。

  2. 此操作将处理它。例如,通过引发带有文本“ interrupted”的IOException。

  3. 操作会做一些奇怪的事情。如上面的代码片段所示,它只是代码。您可以捕获InterruptedException而什么也不做,从而清除该标志而不实际结束。 interrupt()方法不会强制关闭或停止任何操作,Thread上也没有方法可以强制停止它。内置代码(java.*程序包中的东西)均不执行此类操作;他们总是忽略它,抛出InterruptedException被指定这样做,否则抛出相关异常;几乎总是IOException