线程池ThreadPoolTaskExecutor的使用

定义线程池

在spring的配置文件中定义Bean

<!-- 配置线程池 -->
<bean id="taskExecutor"
      class="org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor">
    <!-- 线程池维护线程的最少数量 -->
    <property name="corePoolSize" value="${taskExecutor.corePoolSize}" />
    <!-- 线程池维护线程所允许的空闲时间 -->
    <property name="keepAliveSeconds" value="${taskExecutor.keepAliveSeconds}" />
    <!-- 线程池维护线程的最大数量 -->
    <property name="maxPoolSize" value="${taskExecutor.maxPoolSize}" />
    <!-- 线程池所使用的缓冲队列 -->
    <property name="queueCapacity" value="${taskExecutor.queueCapacity}" />
    <!-- 子线程是否允许超时,必须允许 -->
    <property name="allowCoreThreadTimeOut" value="true" />
    <property name="rejectedExecutionHandler">
        <bean class="java.util.concurrent.ThreadPoolExecutor.DiscardOldestPolicy"/>
    </property>
</bean>

system.properties

taskExecutor.corePoolSize=3
taskExecutor.maxPoolSize=3
taskExecutor.queueCapacity=50
taskExecutor.keepAliveSeconds=100

使用

taskExecutor主要有两个方法,

  • execute(Runnable task)//无返回值
  • submit(Callable task) // 有返回值
/**
 * 项目初始化完成 监听器
 * 启动消费者线程
 * Author: Erik Yu
 * Date:2018/11/19 16:43
 */
@Component
public class ApplicationContextFinishedListener implements ApplicationListener<ContextRefreshedEvent> {
    
    
    private static Logger logger = Logger.getLogger(ApplicationContextFinishedListener.class);
    @Autowired
    private ThreadPoolTaskExecutor taskExecutor;

    @Override
    public void onApplicationEvent(ContextRefreshedEvent event) {
    
    
        if(event.getApplicationContext().getParent() == null){
    
    
            //启动消费者线程
            logger.info("应用启动成功,开始启动任务消费者线程");
            taskExecutor.submit(new ReportConsumer());
        }
    }
}

应用停止时关闭线程池

@WebListener
public class TaskExectorStopListener implements ServletContextListener {
    
    
    private static Logger logger = Logger.getLogger(TaskExectorStopListener.class);

    @Autowired
    private ThreadPoolTaskExecutor taskExecutor;

    @Override
    public void contextInitialized(ServletContextEvent sce) {
    
    
    }

    @Override
    public void contextDestroyed(ServletContextEvent sce) {
    
    
        logger.info("线程池关闭。。。。。");
        taskExecutor.shutdown();
    }
}

注意

一定要记得在应用退出的时候关闭线程池

猜你喜欢

转载自blog.csdn.net/zhaopeng_yu/article/details/89852419