java使用spring框架ThreadPoolTaskExecutor线程池

前言:

spring框架中的ThreadPoolTaskExecutor只是对jdk线程池ThreadPoolExecutor的包装

第一种使用方法:

1、springboot启动类中添加线程池配置

	/**
	 * 定义线程池
	 * @return
	 */
	@Bean("testThreadPool")
	public Executor asyncServiceExecutor() {
		ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
		executor.setCorePoolSize(10);//配置核心线程数
		executor.setMaxPoolSize(20);//配置最大线程数
		executor.setKeepAliveSeconds(5);
		executor.setQueueCapacity(200);//配置队列大小
		executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());//拒绝策略
		executor.setWaitForTasksToCompleteOnShutdown(true);
		executor.initialize();//执行初始化
		return executor;
	}

2、注入ThreadPoolTaskExecutor对象

    @Autowired
    private ThreadPoolTaskExecutor threadPoolTaskExecutor;

3、其他方法和jdk的线程池使用方式相同。

具体参考:https://blog.csdn.net/sumengnan/article/details/105156397中的demo

 

第二种使用方法:

1、springboot启动类中添加线程池配置和@EnableAsync注解

	/**
	 * 定义线程池
	 * @return
	 */
	@Bean("testThreadPool")
	public Executor asyncServiceExecutor() {
		ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
		executor.setCorePoolSize(10);//配置核心线程数
		executor.setMaxPoolSize(20);//配置最大线程数
		executor.setKeepAliveSeconds(5);
		executor.setQueueCapacity(200);//配置队列大小
		executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());//拒绝策略
		executor.setWaitForTasksToCompleteOnShutdown(true);
		executor.initialize();//执行初始化
		return executor;
	}

2、业务方法上使用@Async注解

package com.sumengnan.test.service;

import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.AsyncResult;
import org.springframework.stereotype.Service;

import java.util.concurrent.Future;
import java.util.concurrent.atomic.AtomicInteger;
@Service
public class TestServiceImpl {
    //volatile保证了静态变量的可见性(visibility),
    public static volatile AtomicInteger i = new AtomicInteger(0);

    /**
     * 无返回结果
     */
    @Async("testThreadPool")
    public void test() {
        try {
            Thread.sleep(500);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println("当前第"+ i.incrementAndGet() +"次执行");
    }

    /**
     * 有返回结果
     * @return
     */
    @Async("testThreadPool")
    public Future<String> test2() {
        try {
            Thread.sleep(500);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        return new AsyncResult("当前第"+ i.incrementAndGet() +"次执行");
    }
}

 3、直接调用异步方法即可

package com.sumengnan.test.web;

import com.sumengnan.test.service.TestServiceImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Future;
import java.util.concurrent.atomic.AtomicInteger;

@RestController
public class TestController {
    @Autowired
    private TestServiceImpl testServiceImpl;
    /**
     * 无返回值
     * @param request
     */
    @GetMapping("test")
    public void test(HttpServletRequest request){
        TestServiceImpl.i=new AtomicInteger(0);
        //循环230次
        for (int i = 0; i <230; i++) {
            System.out.println("第"+(i+1)+"个任务加入队列");
            testServiceImpl.test();
        }
        System.out.println("已全部加入队列");
    }
    /**
     * 有返回值
     * @param request
     */
    @GetMapping("test2")
    public void test2(HttpServletRequest request) throws ExecutionException, InterruptedException {
        TestServiceImpl.i=new AtomicInteger(0);
        //循环230次
        for (int i = 0; i <230; i++) {
            System.out.println("第"+(i+1)+"个任务加入队列");
            Future<String> future = testServiceImpl.test2();
            System.out.println(future.get());
        }
        System.out.println("已全部加入队列");
    }
}

看结果:

注意:

关于@Async注解失效需要注意以下几点:

    1,注解的方法必须是public方法。

    2,方法一定要从另一个类中调用,也就是从类的外部调用,类的内部调用是无效的。因为@Transactional和@Async注解的实现都是基于Spring的AOP,而AOP的实现是基于动态代理模式实现的。那么注解失效的原因就很明显了,有可能因为调用方法的是对象本身而不是代理对象,因为没有经过Spring容器。

   3,异步方法使用注解@Async的返回值只能为void或者Future。

 

 

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值