Ram*_*n R 5 java eclipse spring spring-mvc
我正在为贸易自动化站点构建 Spring 4 Rest API。
在服务层,使用 SpringTaskScheduler.schedule(Runnab??le arg0, Date arg1)接口动态创建一个 cronjob ,它将创建一个Runnable, 在作为参数给出的时间执行,恰好一次。这个线程将调用另一个服务来访问我的 Hibernate DAO 层并在将来做一些事情。
下面给出配置类和实现。
@Configuration
@EnableWebMvc
@EnableScheduling
@ComponentScan("com.example")
public class SpringMvcConfig extends WebMvcConfigurerAdapter {
@Bean
public ThreadPoolTaskScheduler taskScheduler() {
return new ThreadPoolTaskScheduler();
}
}
@Service
public class TransactionServiceImp implements TransactionService {
@Autowired
private TaskScheduler scheduler; //org.springframework.scheduling.TaskScheduler;
@Autowired
private TaskExecutorService taskService; //My service
@Transactional
public myFunction(){
//some code
final Long key = //some id value from db
Date exeTime = //some java.util.Date in future
Runnable runnable = new Runnable() {
private long id = key;
public void run() {
taskService.doSomething(id);
}
};
ScheduledFuture<?> sheduler = scheduler.schedule(runnable, exeTime);
//some code
}
}
Run Code Online (Sandbox Code Playgroud)
这段代码运行良好,并在准确的时间和恰好一次执行任务。
通过eclipse调试,发现每次scheduler.schedule()调用都会创建一个新的daemon线程(处理http请求到spring mvc的时候)。我的问题是,
我的想法是否正确,jvm 在每次
scheduler.schedule()调用时创建新的守护线程 (而不是在指定的日期时间创建线程)?
Running即使在任务执行之后,创建的守护线程仍然在 Eclipse 调试中显示状态。线程是否会在完成run()方法中被破坏?否则,这会是一个性能问题吗?
ThreadPoolTaskScheduler 围绕ScheduledThreadPoolExecutor(底层 jdk 实现)进行包装,可以从预定义的工作线程集中重用线程。每个任务都分配/处理到工作队列。
甚至核心线程也只有在新任务到达时才最初创建和启动
我的想法是否正确,jvm 在每个 Scheduler.schedule() 调用上创建新的守护线程(而不是在指定的日期时间创建线程)?
您每次都创建线程实例(Runnable),因为它接受可运行的,因此您的任务应该被执行,或者队列中的现有工作线程可能处于空闲状态。如果达到最大池大小,您的任务将等待。
即使任务执行后,创建的守护线程在 Eclipse 调试中仍显示“运行”状态。完成 run() 方法后线程是否会被销毁?
Java 文档是这样说的,
一旦调度程序关闭或返回的 ScheduledFuture 被取消,执行就会结束。
否则,这会是性能问题吗?可以运行的最大最佳线程数受 cpu 核心的限制。因此,增加池大小并不一定会提高性能
https://docs.oracle.com/javase/7/docs/api/java/util/concurrent/ScheduledThreadPoolExecutor.html