当前位置: 首页 > 知识库问答 >
问题:

ScheduledExecutorService只运行一次

甄胡非
2023-03-14

我希望一个进程在我启动我的网络服务后运行,然后每隔30分钟左右运行一次(我现在用较小的延迟测试它,只是为了看看它是否工作),但是我的进程从来不会运行超过一次。我做错了什么?

这是我的密码:

@WebListener
public class SchedulerService implements ServletContextListener{

    @Autowired
    UpdateSubscriberService updateSubscriberService;

    ScheduledExecutorService scheduledExecService;

    public SchedulerService(){
        scheduledExecService = Executors.newSingleThreadScheduledExecutor();
    }

    @Override
    public void contextDestroyed(ServletContextEvent arg0) {
        scheduledExecService.shutdown();
    }

    @Override
    public void contextInitialized(ServletContextEvent arg0) {
        scheduledExecService.scheduleWithFixedDelay(new Runnable(){
            @Override
            public void run() {
                Date date = new Date(System.currentTimeMillis());
                System.out.println("Running scheduled update check " + date.toString());
                updateSubscriberService.checkForUpdates();
            }
        }, 60, 30, TimeUnit.SECONDS);
    }
}

共有2个答案

段干麒
2023-03-14

如果您遇到这样的情况:即使最后一次运行尚未完成,代码也必须每隔这么多秒运行一次(如果管理不当,可能会非常危险),您可以在计时器内的不同线程中启动进程。下面是示例代码。

ScheduledExecutorService scheduledExecService = newSingleThreadScheduledExecutor();
scheduledExecService.scheduleWithFixedDelay(new Runnable()
{
    @Override
    public void run()
    {
        // This should be in a try-catch because any error here
        // will stop the recurrence
        try
        {
            // The timer will only repeat if the last run is finished. So
            // we put each new process in a different thread than the timer
            // itself, so the last timer call "finishes" as soon as the process
            // leaves the timer's thread.
            Thread t = new Thread(new Runnable()
            {
                public void run()
                {
                    try
                    {
                        android.os.Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
                        MyProcessThatShouldRunEverySoManySecondsNoMatterWhat();
                    }
                    catch (Exception erTimerThread)
                    {
                        Log.e("Error", erTimerThread.toString());
                    }
                }
            });
            t.setPriority(2);
            t.start();
        }
        catch (Exception erTimer)
        {
            Log.e("Error", erTimer.toString());
        }
    }
}, 0, 60, java.util.concurrent.TimeUnit.SECONDS);
薛霄
2023-03-14

请看我对一个类似问题的回答。

只是猜测一下:正在抛出异常。ScheduledExecutorService如果遇到异常,将静默停止,不再执行进一步的计划工作。

run方法的代码应该始终由try-catch包围,以处理和吸收任何抛出的异常。

 @Override
 public void run() {
    try {  // Let no Exception reach the ScheduledExecutorService.
        Date date = new Date(System.currentTimeMillis());
        System.out.println("Running scheduled update check " + date.toString());
        updateSubscriberService.checkForUpdates();
    } catch ( Exception e ) {
        System.out.println( "ERROR - unexpected exception" );
    }
}

慢慢来。从一个run方法开始,该方法只执行系统。出来println

 类似资料:
  • 当我把逻辑放在一个可运行的线程中时,它工作得很好,只是我不能与UI线程交互。所以我试图把所有的东西都放在一个类中,这个类扩展了Task,除了Task只执行一次之外,其他的都可以工作。没有错误,我从Task successed方法获得一条successed消息。 我还尝试在call方法中使task return Boolean为true,但这没有帮助。 请注意,此代码实际上存在于控制器中,但我将其放

  • 我正在使用计划执行服务 以固定速率运行runnable

  • 是否可以只在指定的时间安排一次Spring服务方法?例如,当前时间是下午2点,但当我点击action按钮时,我希望我的服务方法在晚上8点开始。我很熟悉@Schedured注释,我不确定如何编写不定期运行的cron表达式。这个每天晚上8点触发。 有什么建议吗?

  • 问题内容: 我正在尝试实现一个每秒循环的ScheduledExecutorService线程,但是截至目前,它仅循环一次。 我的问题是如何设置它,使其定期循环而不是一次迭代? 另外,如何将连接池传递到线程中,以便每次迭代都可以查询数据库?任何帮助深表感谢。 问题答案: http://docs.oracle.com/javase/1.5.0/docs/api/java/util/concurrent

  • 我有一个代码必须在未来的某个日期执行,比如说我有一个未来的日期,我想在未来的1分钟内执行一段代码,但只执行一次。我知道我需要用java定时器和TimerTask来实现这一点。例如,做这样的事情: 我正在寻找一种优雅的方式来使用SchduledExecutorService,以便有一个特定的池,因为这个池将用于多个调用。有人能帮我吗?