编程语言
首页 > 编程语言> > java-中断线程以等待用户输入,然后退出应用程序

java-中断线程以等待用户输入,然后退出应用程序

作者:互联网

我有两个正在运行的线程,userInputThread等待命令行中的用户输入,并且interrupterThread尝试在启动后1秒钟中断userInputThread.显然,您不能中断被System.in阻止的线程.另一个答案建议在中断线程之前使用System.in.close()关闭System.in.但是,当我运行以下代码时,userInputThread永远不会中断,并且应用程序只是挂起而没有关闭.

class InputInterruptionExample {

    private Thread userInputThread;
    private Thread interrupterThread;

    InputInterruptionExample() {
        this.userInputThread = new Thread(new UserInputThread());
        this.interrupterThread = new Thread(new InterrupterThread());
    }

    void startThreads() {
        this.userInputThread.start();
        this.interrupterThread.start();
    }
    private class UserInputThread implements Runnable {
        public void run() {
            try {
                System.out.println("enter your name: ");
                String userInput = (new BufferedReader(new InputStreamReader(System.in))).readLine();
            } catch (IOException e) {
                System.out.println("Oops..somethign went wrong.");
                System.exit(1);
            }
        }
    }
    private class InterrupterThread implements Runnable {
        public void run() {
            try {
                sleep(1000);
                System.out.println("about to interrupt UserInputThread");
                System.in.close();
                userInputThread.interrupt();
                userInputThread.join();
                System.out.println("Successfully interrupted");
            } catch (InterruptedException e) {
            } catch (IOException ex) {
                System.out.println("Oops..somethign went wrong.");
                System.exit(1);
            }
        }
    }
    public static void main(String[] args) {
        InputInterruptionExample exampleApp = new InputInterruptionExample();
        exampleApp.startThreads();
    }
}

已经有一个类似的question,但是没有确切的答案.

解决方法:

这样就解决了问题:

class InputInterruptionExample {

    private UserInputThread userInputRunnable;
    private Thread userInputThread;
    private Thread interrupterThread;

    InputInterruptionExample() {
        this.userInputRunnable = new UserInputThread();
        this.userInputThread = new Thread(userInputRunnable);
        this.interrupterThread = new Thread(new InterrupterThread());
    }

    void startThreads() {
        this.userInputThread.start();
        this.interrupterThread.start();
    }
    private class UserInputThread implements Runnable {
        private InputStreamReader isr;
        private BufferedReader br;

        UserInputThread() {
            InputStreamReader isr = new InputStreamReader(System.in);
            BufferedReader br = new BufferedReader(isr);
        }

        public void run() {
            try {
                System.out.println("enter your name: ");
                try{
                    String userInput = br.readLine();
                } catch(NullPointerException e) {}
            } catch (IOException e) {
                System.out.println("Oops..somethign went wrong.");
                System.exit(1);
            }
        }
        public void closeBufferdReader() {
            try {
                System.in.close();
            } catch (IOException e) {
                System.out.println("Oops..somethign went wrong in closeBufferdReader() method");
                System.exit(1);
            }
        }
    }
    private class InterrupterThread implements Runnable {
        public void run() {
            try {
                sleep(1000);
                userInputRunnable.closeBufferdReader();                 
                userInputThread.interrupt();
                userInputThread.join();
                System.out.println("Successfully interrupted");
            } catch (InterruptedException e) {}
        }
    }
    public static void main(String[] args) {
        InputInterruptionExample exampleApp = new InputInterruptionExample();
        exampleApp.startThreads();
    }
}

更新:仅当以这种方式拆分BufferedReader时,此方法才有效:

InputStreamReader isr = new InputStreamReader(System.in);
BufferedReader br = new BufferedReader(isr);
String userInput = br.readLine();

由于某些原因,当将readLine()结构编写为单行时,中断似乎不起作用:

this.userInput = (new BufferedReader(new InputStreamReader(System.in))).readLine();

因此,尽管可以中断拆分后的BufferedReader结构中的线程,但现在无法读取用户的输入.

如果有人能够显示出一种能够获取用户输入并在用户未及时提供任何输入(中断器处于睡眠状态时)中断UserInputThread的方法,请执行此操作.

标签:multithreading,concurrency,input,thread-safety,java
来源: https://codeday.me/bug/20191122/2059381.html