zoukankan      html  css  js  c++  java
  • java并发:interrupt进程终止

    interrupt进程终止

    interrupt()源码

        /**
         * Interrupts this thread.
         *
         * <p> Unless the current thread is interrupting itself, which is
         * always permitted, the {@link #checkAccess() checkAccess} method
         * of this thread is invoked, which may cause a {@link
         * SecurityException} to be thrown.
         *
         * <p> If this thread is blocked in an invocation of the {@link
         * Object#wait() wait()}, {@link Object#wait(long) wait(long)}, or {@link
         * Object#wait(long, int) wait(long, int)} methods of the {@link Object}
         * class, or of the {@link #join()}, {@link #join(long)}, {@link
         * #join(long, int)}, {@link #sleep(long)}, or {@link #sleep(long, int)},
         * methods of this class, then its interrupt status will be cleared and it
         * will receive an {@link InterruptedException}.
         *
         * <p> If this thread is blocked in an I/O operation upon an {@link
         * java.nio.channels.InterruptibleChannel InterruptibleChannel}
         * then the channel will be closed, the thread's interrupt
         * status will be set, and the thread will receive a {@link
         * java.nio.channels.ClosedByInterruptException}.
         *
         * <p> If this thread is blocked in a {@link java.nio.channels.Selector}
         * then the thread's interrupt status will be set and it will return
         * immediately from the selection operation, possibly with a non-zero
         * value, just as if the selector's {@link
         * java.nio.channels.Selector#wakeup wakeup} method were invoked.
         *
         * <p> If none of the previous conditions hold then this thread's interrupt
         * status will be set. </p>
         *
         * <p> Interrupting a thread that is not alive need not have any effect.
         *
         * @throws  SecurityException
         *          if the current thread cannot modify this thread
         *
         * @revised 6.0
         * @spec JSR-51
         */
        public void interrupt() {
            if (this != Thread.currentThread())
                checkAccess();
    
            synchronized (blockerLock) {
                Interruptible b = blocker;
                if (b != null) {
                    interrupt0();           // Just to set the interrupt flag
                    b.interrupt(this);
                    return;
                }
            }
            interrupt0();
        }
    
    

    我主要强调一点当线程处于阻塞状态的时候,调用interrupt(),interrupt status 状态会被clear,从true再次变为false。所以对于通过InterruptedException异常
    来中断需要正确的try catch语句。

    正确的阻塞线程中断方式

    package com.java.javabase.thread.base;
    
    
    import lombok.extern.slf4j.Slf4j;
    
    @Slf4j
    public class InterruptTest2 {
    
        public static void main(String[] args) {
            InterruptTest2 test = new InterruptTest2();
            Thread t1 = test.new ThreadOne("t1");
            t1.start();
    
            try {
                Thread.sleep(2000);
                t1.interrupt();
                log.info("Thread t1 state :{} ", t1.getState());
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
    
        }
    
    
        class ThreadOne extends Thread {
            public ThreadOne(String name) {
                super(name);
            }
    
            @Override
            public void run() {
                int i = 0;
    
                try {
                    while (!interrupted()) {
                        Thread.sleep(500);
                        log.info("Thread {}  state :{} ,run {} times", Thread.currentThread().getName(),
                                Thread.currentThread().getState(), i++);
                    }
                } catch (InterruptedException e) {
                    log.info("Thread {}  state :{} ,run {} times", Thread.currentThread().getName(),
                            Thread.currentThread().getState(), i++);
                    e.printStackTrace();
                }
            }
        }
    }
    
    

    返回结果

    2019-07-30 19:52:40,496   [t1] INFO  InterruptTest2  - Thread t1  state :RUNNABLE ,run 0 times
    2019-07-30 19:52:41,000   [t1] INFO  InterruptTest2  - Thread t1  state :RUNNABLE ,run 1 times
    2019-07-30 19:52:41,500   [t1] INFO  InterruptTest2  - Thread t1  state :RUNNABLE ,run 2 times
    2019-07-30 19:52:41,991   [main] INFO  InterruptTest2  - Thread t1 state :TIMED_WAITING 
    2019-07-30 19:52:41,991   [t1] INFO  InterruptTest2  - Thread t1  state :RUNNABLE ,run 3 times
    java.lang.InterruptedException: sleep interrupted
    	at java.lang.Thread.sleep(Native Method)
    	at com.java.javabase.thread.base.InterruptTest2$ThreadOne.run(InterruptTest2.java:36)
    
    

    说明

    while语句在try catch 捕获到InterruptedException异常,就可以处理。

    错误的中断阻塞线程例子

    package com.java.javabase.thread.base;
    
    
    import lombok.extern.slf4j.Slf4j;
    
    @Slf4j
    public class InterruptTest {
    
        public static void main(String[] args) {
            InterruptTest test = new InterruptTest();
            Thread t1 = test.new ThreadOne("t1");
            t1.start();
    
            try {
                Thread.sleep(2000);
                t1.interrupt();
                log.info("Thread state :{} ", t1.getState());
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
    
        }
    
    
        class ThreadOne extends Thread {
            public ThreadOne(String name) {
                super(name);
            }
    
            @Override
            public void run() {
                int i = 0;
                while (!interrupted()) {
                    try {
                        Thread.sleep(500);
                        log.info("Thread {}  state :{} ,run {} times", Thread.currentThread().getName(),
                                Thread.currentThread().getState(), i++);
                    } catch (InterruptedException e) {
                        log.info("Thread {}  state :{} ,run {} times", Thread.currentThread().getName(),
                                Thread.currentThread().getState(), i++);
                        e.printStackTrace();
                    }
                }
            }
        }
    }
    
    

    测试结果

    2019-07-30 19:54:40,189   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 0 times
    2019-07-30 19:54:40,691   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 1 times
    2019-07-30 19:54:41,192   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 2 times
    2019-07-30 19:54:41,686   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 3 times
    2019-07-30 19:54:41,686   [main] INFO  InterruptTest  - Thread state :TIMED_WAITING 
    java.lang.InterruptedException: sleep interrupted
    	at java.lang.Thread.sleep(Native Method)
    	at com.java.javabase.thread.base.InterruptTest$ThreadOne.run(InterruptTest.java:35)
    2019-07-30 19:54:42,187   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 4 times
    2019-07-30 19:54:42,687   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 5 times
    2019-07-30 19:54:43,187   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 6 times
    2019-07-30 19:54:43,687   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 7 times
    2019-07-30 19:54:44,187   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 8 times
    2019-07-30 19:54:44,687   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 9 times
    2019-07-30 19:54:45,187   [t1] INFO  InterruptTest  - Thread t1  state :RUNNABLE ,run 10 times
    

    错误结果说明

    try catch在while语句之内, 捕获到InterruptedException异常,while的!interrupted()会再次返回true

    运行态的线程的终止

    package com.java.javabase.thread.base;
    
    
    import lombok.extern.slf4j.Slf4j;
    
    @Slf4j
    public class InterruptTest3 {
        private boolean stopFlag = false;
    
        private void stoptask() {
            this.stopFlag = true;
        }
    
        public static void main(String[] args) {
            InterruptTest3 test = new InterruptTest3();
            Thread t1 = test.new ThreadOne("t1");
            t1.start();
    
            try {
                Thread.sleep(5000);
                test.stoptask();
                log.info("Thread t1 state :{} ", t1.getState());
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
    
        }
    
    
        class ThreadOne extends Thread {
            public ThreadOne(String name) {
                super(name);
            }
    
            int i = 0;
    
            @Override
            public void run() {
                while (!stopFlag) {
                    try {
                        sleep(1000);
                        log.info("Thread {}  state :{} ,run {} times", Thread.currentThread().getName(),
                                Thread.currentThread().getState(), i++);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
    
                }
            }
        }
    }
    
    

    测试结果

    2019-07-30 20:01:19,922   [t1] INFO  InterruptTest3  - Thread t1  state :RUNNABLE ,run 0 times
    2019-07-30 20:01:20,923   [t1] INFO  InterruptTest3  - Thread t1  state :RUNNABLE ,run 1 times
    2019-07-30 20:01:21,923   [t1] INFO  InterruptTest3  - Thread t1  state :RUNNABLE ,run 2 times
    2019-07-30 20:01:22,923   [t1] INFO  InterruptTest3  - Thread t1  state :RUNNABLE ,run 3 times
    2019-07-30 20:01:23,918   [main] INFO  InterruptTest3  - Thread t1 state :TIMED_WAITING 
    2019-07-30 20:01:23,923   [t1] INFO  InterruptTest3  - Thread t1  state :RUNNABLE ,run 4 times
    
  • 相关阅读:
    在linux上搭建sftp服务
    FTP客户端遇到150连接超时错误的处理办法
    电脑每次开机打开微软网站怎么解决
    Linux学习笔记之认识与学习Bash
    Linux学习笔记之VIM编辑器
    Linux学习笔记之文件与文件系统的压缩与打包
    Linux学习笔记之磁盘与文件系统的管理
    Linux学习笔记之目录配置
    Linux学习笔记之档案权限与目录配置
    ubuntu修改apt源
  • 原文地址:https://www.cnblogs.com/JuncaiF/p/11272381.html
Copyright © 2011-2022 走看看