唤醒睡眠线程 - Interrupt() 与将睡眠“拆分”为多个睡眠

2024-03-09

这个要求出现在我的 Android 应用程序中,但它通常适用于 Java。我的应用程序每隔几秒钟就会“做一些事情”。我的实现如下(只是相关片段 - 不是完整的代码):

片段1:

public class PeriodicTask {

    private boolean running = true;
    private int interval = 5;

    public void startTask(){
        while (running){
            doSomething();
            try{
                Thread.sleep(interval * 1000);
            } catch(InterruptedException e){
                //Handle the exception.
            }
        }
    }

    public void stopTask(){
        this.running = false;
    }

    public void setInterval(int newInterval){
        this.interval = newInterval;
    }
}

正如您所看到的,这种方法的问题在于 setInterval() 不会立即生效。它仅在前一个 sleep() 完成后才会生效。

由于我的用例允许最终用户以固定步骤设置间隔(1 秒 - 从 1 到 60 秒),因此我修改了实现以在循环内休眠;并每秒检查新的间隔值,如下所示:

片段2:

public class PeriodicTask {

    private boolean running = true;
    private int interval = 5;
    private int loopCounter = 0;

    public void startTask(){
        while (running){
            doSomething();
            try{
                while(loopCounter < interval) {
                    Thread.sleep(1 * 1000);
                    loopCounter ++;
                }
            } catch(InterruptedException e){
                //Handle the exception.
            }
        }
    }

    public void stopTask(){
        this.running = false;
    }

    public void setInterval(int newInterval){
        synchronized (this) {
            this.interval = newInterval;
            if(newInterval < loopCounter){
                loopCounter = 0;
            }
        }
    }
}

有理由不使用这种方法吗?

我最近遇到了interrupt()用于此目的的方法。但是,我无法确切地弄清楚如何使用它。其一,中断方法与睡眠方法不同,它不是static。所以呢Thread我要打断吗?

public void setInterval(int newInterval){
        this.interval = newInterval;
        //What thread do I call interrupt() on?
    }

其次,如果我确实成功地打扰了睡眠Thread,我相信catch块为InterruptedException将被执行。但是,我需要致电startTask()再次在这一点上。我对这个递归的终止感到困惑。我已经解决了关于使用interrupt()的几个问题,但找不到任何对我有帮助的东西。

有什么指点吗?


编辑-有关确切要求的更多详细信息:

我的应用程序每隔几秒使用 REST 调用获取一些值。更新间隔可由用户配置。

现在,假设更新间隔已设置为 60 秒。我发布的 Snippet1 的工作方式(不正确)如下:

  • 线程进入休眠状态 60 秒。
  • 现在,假设用户将更新间隔更改为 5 秒。线程仍在休眠。
  • The PeriodicTask仅在 60 秒过后才会看到新的更新间隔。

确切的要求是新的更新间隔应立即生效(或至少在设置后不晚于 1 秒 - 因为无论如何用户都可能感知到这一点)。

我的 Snippet2 和 Snippet3 就是尝试实现这个要求。


IIRC,在 Java 中你可以使用 object.wait() 来设置超时。这不是你想要的吗?如果您想更改另一个线程的超时,请更改一些“waitValue”变量和notify()。然后,线程将“立即”运行,然后使用新的超时值再次等待。不需要明确的睡眠。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

唤醒睡眠线程 - Interrupt() 与将睡眠“拆分”为多个睡眠 的相关文章

随机推荐