2

1、ThreadPoolTaskExecutor @Async示例

@Async 注解的作用

  1. 异步执行方法:
    被 @Async 注解标记的方法会在一个独立的线程中执行,而不是在调用者的线程中。这意味着调用方法时,调用者线程会立即返回,并且方法的实际执行会在后台进行
  2. 提高并发性和性能:
    通过异步执行耗时的操作,可以提高应用程序的响应速度和吞吐量。例如,在Web应用中,可以异步处理后台任务,从而更快地响应用户请求
  3. 分离任务执行:
    可以将一些不需要立即返回结果的任务(例如发送邮件、写日志等)异步执行,从而提高应用的整体效率

    1.1、引入依赖

    确保你的项目中引入了Spring的相关依赖。对于Maven项目,pom.xml中需要包含以下依赖:

<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter</artifactId>
  <version>2.7.3</version>
</dependency>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-web</artifactId>
  <version>2.7.3</version>
</dependency>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-configuration-processor</artifactId>
  <version>2.7.3</version>
</dependency>

1.2、ThreadPoolTaskExecutor配置类

@Configuration
public class AppConfig {

    @Bean(name = "taskExecutor")
    public Executor taskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
        executor.setCorePoolSize(5);
        executor.setMaxPoolSize(10);
        executor.setQueueCapacity(25);
        executor.setThreadNamePrefix("MyExecutor-");
        executor.initialize();
        return executor;
    }
}

1.3、@Async ThreadPoolTaskExecutor执行任务

@Service
public class TaskService {

    @Autowired
    private Executor taskExecutor;

    @Async("taskExecutor")
    public void executeTask(int i) {
        System.out.println("Task " + i + " is running on thread " + Thread.currentThread().getName());
    }
}

1.4、启用异步支持

为了让Spring支持异步调用,需要在配置类中启用异步支持:

@Configuration
@EnableAsync
public class AsyncConfig {
}

1.5、启动任务 & 结果

@SpringBootApplication
public class Application implements CommandLineRunner {

    @Autowired
    private TaskService taskService;

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }

    @Override
    public void run(String... args) {
        for (int i = 0; i < 10; i++) {
            taskService.executeTask(i);
        }
    }
}

结果如下 :

Task 0 is running on thread MyExecutor-1
Task 2 is running on thread MyExecutor-3
Task 3 is running on thread MyExecutor-4
Task 7 is running on thread MyExecutor-4
Task 4 is running on thread MyExecutor-5
Task 8 is running on thread MyExecutor-4
Task 6 is running on thread MyExecutor-3
Task 1 is running on thread MyExecutor-2
Task 5 is running on thread MyExecutor-1
Task 9 is running on thread MyExecutor-5

1.6、不使用@Async注解的任务提交

@Service
public class TaskService {

    @Autowired
    private Executor taskExecutor;

//    @Async("taskExecutor")
//    public void executeTask(int i) {
//        System.out.println("Task " + i + " is running on thread " + Thread.currentThread().getName());
//    }

    public void executeTask(int i) {
        taskExecutor.execute(() -> {
            System.out.println("Task " + i + " is running on thread " + Thread.currentThread().getName());
        });
    }
}

2、ThreadPoolTaskExecutor submitListenable

2.1、代码逻辑

@Configuration
public class AppConfig {

    @Bean(name = "taskExecutor")
    public ThreadPoolTaskExecutor taskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
        executor.setCorePoolSize(5);
        executor.setMaxPoolSize(10);
        executor.setQueueCapacity(25);
        executor.setThreadNamePrefix("MyExecutor-");
        executor.initialize();
        return executor;
    }
}
public class Task implements Callable<String> {

    private final int taskId;

    public Task(int taskId) {
        this.taskId = taskId;
    }

    @Override
    public String call() throws Exception {
        System.out.println("Task " + taskId + " is running on thread " + Thread.currentThread().getName());
        // Simulate a long-running task
        Thread.sleep(1000);
        return "Task " + taskId + " completed";
    }
}
@SpringBootApplication
public class Application implements CommandLineRunner {

    @Autowired
    private ThreadPoolTaskExecutor taskExecutor;


    public static void main(String[] args) throws Exception {
        SpringApplication.run(Application.class, args);
    }

    @Override
    public void run(String... args) throws Exception {

        List<ListenableFuture<String>> futures = new ArrayList<>();
        for (int i = 0 ; i < 10 ; i++) {
            Task task = new Task(i);
            ListenableFuture<String> future = taskExecutor.submitListenable(task);
            future.addCallback(new ListenableFutureCallback<String>() {
                @Override
                public void onFailure(Throwable ex) {
                    System.out.println("onFailure ex ->" + ex);
                }

                @Override
                public void onSuccess(String result) {
                    System.out.println("onSuccess  result -> " + result);
                }
            });
        }
    }
}

2.2、结果输出

Task 0 is running on thread MyExecutor-1
Task 1 is running on thread MyExecutor-2
Task 2 is running on thread MyExecutor-3
Task 3 is running on thread MyExecutor-4
Task 4 is running on thread MyExecutor-5
onSuccess  result -> Task 1 completed
Task 5 is running on thread MyExecutor-2
onSuccess  result -> Task 2 completed
Task 6 is running on thread MyExecutor-3
onSuccess  result -> Task 3 completed
Task 7 is running on thread MyExecutor-4
onSuccess  result -> Task 4 completed
Task 8 is running on thread MyExecutor-5
onSuccess  result -> Task 0 completed
Task 9 is running on thread MyExecutor-1
onSuccess  result -> Task 5 completed
onSuccess  result -> Task 9 completed
onSuccess  result -> Task 6 completed
onSuccess  result -> Task 7 completed
onSuccess  result -> Task 8 completed

如感兴趣,点赞加关注,谢谢!!!


journey
32 声望20 粉丝