Java:如何中断/停止线程?

Val*_*lva 15 java multithreading

我试图阻止一个线程,但我不能这样做:

public class Middleware {

public void read() {
    try {
        socket = new Socket("192.168.1.8", 2001);

        // code .. 

        Scan scan = new Scan();
        thread = new Thread(scan);
        thread.start();

    } catch (UnknownHostException ex) {
        ex.printStackTrace();

    } catch (IOException ex) {
        ex.printStackTrace();
    }
}

class Scan extends Thread {

    public void run() {

        while (true) {
            try {
            // my code goes here

            } catch (IOException ex) {
                thread.currentThread().interrupt();
            }
        }
    }
}

public void stop() {
    Thread.currentThread().interrupt();
}

// get and setters
}
Run Code Online (Sandbox Code Playgroud)

所以,即使我调用方法'停止',线程也不会停止.它保持活力.

我该如何中断/停止此线程?

更新 (@little方法)

private void tb_startActionPerformed(java.awt.event.ActionEvent evt) {                                         
    Middleware middleware = new Middleware();

    if (tb_start.getText().equals("Start")){
        tb_start.setText("Stop");

        // starting to read rfid tags
        middleware.read();
    }else{
        tb_start.setText("Start");

        // stop reading rfid tags
        middleware.stop();
    }
}
Run Code Online (Sandbox Code Playgroud)

中间件类:

public class Middleware {

    private Scan scan;

    public void read() {

        scan = new Scan();
        scan.start();
    }

    private class Scan extends Thread {

        @Override
        public void run() {
            while (!Thread.currentThread().isInterrupted()) {
                System.out.println("reading...");
            }
        }
    }

    public void stop() {
        if (scan != null) {
            scan.interrupt();
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

但是当我试图阻止线程时,它没有.上面的代码可能有什么问题?

此致,Valter Henrique.

mre*_*mre 20

你真的没有理由需要使用volatile旗帜.相反,只需查询线程的状态isInterrupted().另外,为什么要将Scan线程对象包装在另一个线程对象中?这对我来说似乎完全没用.

这是'你应该做的

public class Middleware {
    private Scan scan;

    public void read() {
        try {
            // do stuff

            scan = new Scan();
            scan.start();
        } catch (UnknownHostException ex) {
            // handle exception
        } catch (IOException ex) {
            // handle exception
        }
    }

    private class Scan extends Thread {

        @Override
        public void run() {
            while (!Thread.currentThread().isInterrupted()) {
                try {
                    // my code goes here
                } catch (IOException ex) {
                    Thread.currentThread().interrupt();
                }
            }
        }
    }

    public void stop() {
        if(scan != null){
            scan.interrupt();
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

这是一个例子.另外,我不建议延长Thread.


Leo*_*ngs 10

只需return;从你的while和线程将死亡,无需调用stop()或interrupt().如果您想在外部执行此操作,请使用此模式并调用requestStop().

class Scan extends Thread {
    private volatile stop = false;
    public void run() {

        while (!stop) {
            try {
            // my code goes here

            } catch (IOException ex) {
                stop = true;
            }
        }
    }

    public void requestStop() {
        stop = true;
    }

}
Run Code Online (Sandbox Code Playgroud)

  • 在requestStop方法中将stop设置为true后,可以添加`interrupt()`调用. (2认同)

tra*_*god 5

" stop()应该用简单修改某个变量的代码替换许多用途,以指示目标线程应该停止运行." -java.lang.Thread


Jim*_*Jim 5

停止线程的常用方法是有一个 volatile 标志,然后在 run 方法中检查它。IE

class Scan extends Thread {
    volatile stop = false;
    public void run() {

        while (!stop) {
            try {
            // my code goes here

            } catch (IOException ex) {
                thread.currentThread().interrupt();
            }
        }
    }

    public void stop(){
        stop = true;
    }
}
Run Code Online (Sandbox Code Playgroud)

然后就可以调用了scan.stop()


Ana*_*rma 5

如果要中断正在运行的线程,则需要访问该线程对象.

__CODE__ 然后说

__CODE__

这将中断正在运行的线程.