如何停止ScheduledExecutorService?

时间:2015-12-10 13:06:30

标签: java executorservice

该程序在九次打印后完成:

class BeeperControl {

    private final ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1);

    public void beep() {
        final Runnable beeper = new Runnable() {
            public void run() {
                System.out.println("beep");
            }
        };
        final ScheduledFuture<?> beeperHandle = scheduler.scheduleAtFixedRate(
                beeper, 1, 1, SECONDS);
        scheduler.schedule(new Runnable() {
            public void run() {
                beeperHandle.cancel(true);
            }
        }, 1 * 9, SECONDS);
    }

    public static void main(String[] args) {
        BeeperControl bc = new BeeperControl();
        bc.beep();
    }
}

如何停止进程(例如eclipse中的java进程),因为它在9秒内没有停止时间?

1 个答案:

答案 0 :(得分:16)

您遇到的问题是,在取消蜂鸣声任务后,调度程序会保留一个实时线程。

如果存在实时非守护程序线程,则JVM保持活动状态。

它保留这个线程的原因是你告诉它在这一行中这样做:

private final ScheduledExecutorService scheduler
        = Executors.newScheduledThreadPool(1);

请注意newScheduledThreadPool(int corePoolSize)的文档:

  

corePoolSize - 池中保留的线程数,即使它们处于空闲状态。

因此,您有两种方法可以使JVM终止:

  1. 0传递给newScheduledThreadPool而不是1.调度程序不会保留活动线程,JVM将终止。

  2. 关闭调度程序。无论如何,你应该这样做才能释放它的资源。因此,请将匿名run中的Runnable更改为:

    public void run() {
        beeperHandle.cancel(true);
        scheduler.shutdown();
    }
    
  3. (事实上,你不需要cancel - shutdown会在下一次&#34;哔声&#34;完成后立即生效。)