如何在不使用Java线程的情况下定期安排任务?

时间:2016-04-26 19:25:16

标签: java scheduled-tasks

我正在开发一个Java程序,要求我安排定期执行任务。但限制是我不能使用线程。

我遇到过Timer和TimerTask,但我不确定他们是否创建了线程..

有没有办法在不使用线程的情况下完成此操作?

提前致谢。

4 个答案:

答案 0 :(得分:2)

所有Java计时器,甚至是Swing Timer,都使用一个单独的线程来等待并在适当的时间触发事件。

如果程序必须定期执行某些操作,但无法启动新线程,那么主线程必须执行此操作。

但是,可以吗?它在做什么呢?

如果主线程处于空闲状态,您可以计算下一次事件之前的时间量,并计算sleep之前的时间。

答案 1 :(得分:0)

这取决于您的应用程序设计。一种可能的方法是将您的应用程序设计为要执行的任务。并使用Cron作业(类Unix计算机操作系统中基于时间的作业调度程序)启动它。

答案 2 :(得分:0)

您可以尝试使用Quartz调度程序。虽然它在内部使用线程池。它稳定而有效。

答案 3 :(得分:0)

Thread.sleep

the answer by Andreas所述,您可以重复睡眠当前线程以执行重复任务。我理解你的情况是家庭作业课程中的指定要求,不使用线程。我假设分配的目的是不使用其他线程。您执行的代码始终在一个线程中。每个Java应用程序都以JVM提供的初始线程开始。

但你应该知道,在实际工作中,“没有更多线程”的要求是愚蠢的;线程的目的是在不同的时间框架上执行任务。因此,对于实际工作,我会推荐其他更优雅,更灵活,更强大的方法(搜索Java ExecutorsScheduledExecutorService)。

但是对于你的作业,Thread类确实提供了一个静态方法sleep,用于使当前线程进入休眠状态。

InstantUTC中时间轴上的一个时刻,分辨率高达纳秒。 Java 8及更高版本中内置的java.time框架的一部分。可用于Java 6和Java 6的后端口7和Android。

TimeUnit枚举使转换为毫秒自我记录。

请注意,休眠线程可能被另一个线程或JVM唤醒。发生这种情况时,唤醒的线程会遇到InterruptedException

long millisToSleep = java.util.concurrent.TimeUnit.MINUTES.toMillis ( 5 );

Instant now = Instant.now ();
Instant limit = now.plus ( 1 , ChronoUnit.HOURS );

while ( Instant.now ().isBefore ( limit ) ) {
    System.out.println ( "Doing some stuff at " + Instant.now () );
    // … do some stuff.
    System.out.println ( "Going to sleep for " + millisToSleep + " milliseconds." );
    try {
        Thread.sleep ( millisToSleep );  // I do not recommend this approach, but it works. Better to use a 'ScheduledExecutorService'.
    } catch ( InterruptedException ex ) {
        System.out.println ( "This thread’s sleep was rudely interrupted at " + Instant.now () + ". Stopping any further work." );
        break; // Bail out of the 'while' loop.
    }
}