Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何使用ScheduledExecutorService在特定时间段内运行任务?_Java_Scheduled Tasks_Scheduledexecutorservice - Fatal编程技术网

Java 如何使用ScheduledExecutorService在特定时间段内运行任务?

Java 如何使用ScheduledExecutorService在特定时间段内运行任务?,java,scheduled-tasks,scheduledexecutorservice,Java,Scheduled Tasks,Scheduledexecutorservice,我正在尝试创建一个计划作业,每天从早上7点到晚上22点每5分钟运行一次。例如,它应该在7:00、7:05、7:10运行。。。21:55,然后在22:00停止。第二天,它再次运行相同的时间表,以此类推 我发现了这个示例,它演示了如何使用ScheduledExecutorService在特定时间启动任务。 我参考答案,编写代码如下: (我正在使用Java7) 类调度程序{ 专用ScheduledExecutorService执行器; 公共静态void main(字符串[]arg){ Runnabl

我正在尝试创建一个计划作业,每天从早上7点到晚上22点每5分钟运行一次。例如,它应该在7:00、7:05、7:10运行。。。21:55,然后在22:00停止。第二天,它再次运行相同的时间表,以此类推

我发现了这个示例,它演示了如何使用
ScheduledExecutorService
在特定时间启动任务。

我参考答案,编写代码如下: (我正在使用Java7)

类调度程序{
专用ScheduledExecutorService执行器;
公共静态void main(字符串[]arg){
Runnable任务=新的Runnable(){
@凌驾
公开募捐{
…做点什么。。。
}
};
//获取下一个开始时间(上午7点)前的秒数。
long initDelay=getInitialDelay(7);
ScheduledExecutorService executors=executors.newSingleThreadScheduledExecutor();
executors.scheduleAtFixedRate(任务,初始延迟,(60*5),时间单位为秒);
}
专用静态长getInitialDelay(整数小时){
Calendar calNow=Calendar.getInstance();
Calendar cal=Calendar.getInstance();
校准设置(日历小时/天,小时);
校准设置(日历分钟,0);
校准设置(日历秒,0);
long diff=cal.getTimeInMillis()-calNow.getTimeInMillis();
如果(差异<0){
cal.add(日历日/月,1);
diff=cal.getTimeInMillis()-calNow.getTimeInMillis();
}
返回差/1000;
}
}
我上面的代码从早上7点开始,每5分钟运行一次。但是,如何控制ScheduledExecuterService在晚上22点停止任务,然后在第二天早上7点重新开始


或者,有没有其他更好的方法在每天的特定时间段运行任务?

固定计划执行器服务不能改变其时间

因此,请使用单次运行的非固定计划执行器服务。呼叫在第一次运行时,检查当前时间。如果在工作日结束前,再次调用相同的方法
schedule
,延迟五分钟。如果在工作日结束后,延迟8小时,则为新工作日开始前的时间量


所以,一个简单的小把戏。runnable的每次跑步都会无休止地安排下一次跑步

顺便说一下,
Calendar
是一个糟糕的类,几年前,随着JSR310的采用,它被现代的java.time类所取代。对于Java 6和Java 7,请参阅Three Ten Backport项目。您的意思是我应该创建嵌套的执行器吗?@edyucheng Nope,只有一个
ScheduledExecutorService
对象。只有一个可运行的对象。您的
Runnable
可以调用
schedule
方法来安排自己的下一次运行。明天我可能会写一个例子,尽管一些关于堆栈溢出的答案已经说明了这一点。或者你可以想清楚,因为这真的很简单。检查
run
方法中的时间。在安排下一次运行并运行下一次运行后,如何再次调用
schedule
方法?我试图使用一个无限循环并将
schedule
方法放入其中,但它显示了错误。
while(true){executor.schedule(task,5,TimeUnit.MINUTE);}
。你能演示一下如何控制并举例说明吗?非常感谢你!
class Scheduler {
    private ScheduledExecutorService executors;

    public static void main(String[] arg) {
       Runnable task = new Runnable() {
            @Override
            public void run() {
                ...DO SOMETHING...
            }
       };
        
       // Get how many seconds before the next start time (7AM).
       long initDelay = getInitialDelay(7); 
       
       ScheduledExecutorService executors = Executors.newSingleThreadScheduledExecutor();
       executors.scheduleAtFixedRate(task, initDelay, (60 * 5), TimeUnit.SECONDS);
   }

    private static long getInitialDelay(int hour) {
        Calendar calNow = Calendar.getInstance();

        Calendar cal = Calendar.getInstance();
        cal.set(Calendar.HOUR_OF_DAY, hour);
        cal.set(Calendar.MINUTE, 0);
        cal.set(Calendar.SECOND, 0);

        long diff = cal.getTimeInMillis() - calNow.getTimeInMillis();
        if (diff < 0) {
            cal.add(Calendar.DAY_OF_MONTH, 1);
            diff = cal.getTimeInMillis() - calNow.getTimeInMillis();
        }

        return diff / 1000;
    }
}