首页 | 新闻 | 新品 | 文库 | 方案 | 视频 | 下载 | 商城 | 开发板 | 数据中心 | 座谈新版 | 培训 | 工具 | 博客 | 论坛 | 百科 | GEC | 活动 | 主题月 | 电子展
返回列表 回复 发帖

Thread.sleep、Object.wait、LockSupport.park 区别3

Thread.sleep、Object.wait、LockSupport.park 区别3

题外话:关于java进程的关闭

在linux中,我们通常用kill命令来关闭一个进程。众所周知,kill有-9和-15两种参数,默认是-15。如果是-15参数,系统就发送一个关闭信号给进程,然后等待进程关闭。在这个过程中,目标进程可以释放手中的资源,以及进行一些关闭操作。

正是有了这个概念,我曾经很大一段时间对java进程的关闭流程有所误解。在我原先的理解中,java进程接收到关闭信号后,会逐一给阻塞中的进程发送中断信号,并等待线程处理完。但其实这是错误的。

java进程收到关闭信号后,不会去关心运行中的那些线程是否运行完,也不会给阻塞中的线程发送中断信号。我们只能通过绑定关闭钩子来中断目标线程并等待线程执行完。

    final Thread waitThread = new Thread(new Runnable() {
                @Override
                public void run() {
                    System.out.println("thread begin");
     
                    //等待获取许可
                    try {
                        Thread.sleep(1000000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    //输出thread over.true
                    System.out.println("thread over." + Thread.currentThread().isInterrupted());
     
                    try {
                        Thread.sleep(3000);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            });
            waitThread.start();
            //绑定钩子
            Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
                @Override
                public void run() {
                    try {
                        waitThread.interrupt();
                        waitThread.join();
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                    System.out.println("shutdown success");
                }
            }));

java进程在收到关闭信号后,会执行所有绑定了shutdownHook的线程,确保这些绑定的线程都执行完了才真正关闭。因此,我们要释放资源就要在shutdownHook的线程内操作,然后在线程内等待其他释放资源的线程执行完成。

注意,所有绑定了shutdownHook的线程也是并行执行的,不是顺序执行。另外,用-9参数的kill不会等shutdownHook线程执行完就退出。
返回列表