Java Spring中@Scheduled方法内的Thread.sleep
我有一个方法,计划每运行一个X毫秒 此方法正在新线程中启动新方法 然而,我想在再次计数之前推迟这个方法 这是我的密码:Java Spring中@Scheduled方法内的Thread.sleep,java,spring,multithreading,spring-boot,scheduled-tasks,Java,Spring,Multithreading,Spring Boot,Scheduled Tasks,我有一个方法,计划每运行一个X毫秒 此方法正在新线程中启动新方法 然而,我想在再次计数之前推迟这个方法 这是我的密码: @Scheduled(fixedRate = RATE_IN_MS) public void myMethod(){ new Thread(() -> method()).start(); Thread.sleep(RATE_IN_MS); } 问题是,这种行为与我想要的不一样 以下是当前的行为: 在启动RATE_IN_MS myMethod后 方法()
@Scheduled(fixedRate = RATE_IN_MS)
public void myMethod(){
new Thread(() -> method()).start();
Thread.sleep(RATE_IN_MS);
}
问题是,这种行为与我想要的不一样
以下是当前的行为:
谢谢!使用
fixedRate
,调度程序不关心在myMethod
中花费的时间
您可以使用
@Scheduled(fixedDelay=RATE_IN_MS)
。计划程序将在完成myMethod
后计算下一次执行时间。我创建了这个运行示例供您参考。执行延迟在spring配置文件中配置,可以根据您的意愿进行更改
package com.myprgm;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.scheduling.TaskScheduler;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
import org.springframework.stereotype.Component;
@Component
@EnableScheduling
public class JobSchdulingServc {
@Value("${com.executionDelay}")
private long executionDelay; // in milliseconds,mention in sping property file
@Autowired
TaskScheduler taskScheduler;
@Bean
public TaskScheduler poolScheduler() {
return new ThreadPoolTaskScheduler();
}
private void stopSceduling(boolean terminateJob) {
((ThreadPoolTaskScheduler) taskScheduler).shutdown();
if (terminateJob) {
System.exit(1);
}
}
public void scheduleMyJob() {
taskScheduler.scheduleWithFixedDelay(new Runnable() {
@Override
public void run() {
try {
someServiceimpl.generateMyDataAndSendInEveryMilliSeconds(); // service you want to execute after
// specified executionDelay
} catch (Exception e) {
stopSceduling(true);
}
}
}, executionDelay);
}
}
当使用
fixedrate
调度时,有两种可能的情况,即下次调用myMethod
的时间:
myMethod
后RATE\u IN_MS
毫秒,myMethod
不再运行,则此时将再次调用myMethod
myMethod
调用的RATE_IN_MS
毫秒后,该调用仍在运行且未返回,则这将导致下一个计划调用被阻止,直到当前调用结束myMethod
执行需要5毫秒。在这种情况下,每10毫秒将发生一次新的myMethod
调用,因为5毫秒小于10毫秒myMethod
调用需要12毫秒才能完成,这比10毫秒长,那么下一次调用将排队。因此,调用之间至少有12毫秒的间隔,这比RATE\u IN\u ms
长RATE_IN_MS
为10 MS,那么我们肯定有上面示例中的第二种情况,但是,等待时间不会像您预期的那样乘以两倍,而是由两个时间段组成:
myMethod
到达Thread.sleep(RATE_IN_MS)
所用的时间可能比RATE_IN_MS
要少得多,假设它只有3毫秒,我们把这个时间称为XRATE_IN_MS
,例如,我们说它是10ms然后是调用
myMethod()之间的总时间
将是:X+RATE\u IN\u MS
,根据我的示例,它是13 MS,而不是RATE\u IN\u MS
*2。@ShanuGupta-为什么?我使用的是相同的常量RATE\u IN\u MS。此外,为什么它们彼此相关?即使我想为RATE\u IN\u MS/2睡觉,它也需要是正常的。因为,无论发生什么情况,您都是在固定速度下运行的执行时发生的情况,线程将调用myMethod()。请改用fixedDelay。我理解这一点,但如果睡眠时间将
超过固定速率,它将如何影响此场景?