SpringBoot中 控制器不能使用@Async 或者说同一个类不能使用@Async的原因 真正原因是 @Async 不能在同一个类中直接调用。如果一个类中的方法 A 调用标记为 @Async 的方法 B,B 方法不会以异步方式执行,因为它不会通过代理对象 因为 A方法调用B方法时候有个this
@Async 异步开启线程执行
@Async没有真正的线程池 就是来一个然后SimpleAsyncTaskExecutor开一个线程模式,直到资源耗尽
-
无限制地创建线程:
SimpleAsyncTaskExecutor
每次任务都会创建一个新线程,没有限制线程的数量。如果任务非常多,可能导致系统资源耗尽(如内存不足)。 -
线程管理不佳: 由于没有线程池的概念,无法对线程的复用、调度和生命周期进行有效管理。
-
性能问题: 创建和销毁线程的开销比较大,频繁创建新线程可能导致性能下降。
因此定义一个用于@Async的线程池还是有很多好处的
关于参数和返回值
1.@Async方法可以带参数 例如
2.@Async方法可以有返回值, 但返回类型必须是 java.util.concurrent.Future
、
这样等待返回结果有意义么 那还不如同步 使用场景不多
关于@Scheduled 是Spring task里的注解
这样每隔5秒执行一次
如果是下面这种情况会发生什么
如果test2 或者test3先被加载到 队列 那么test2或者test3会执行一次
接着这个线程就一直被test占用 也就是说test任务没有完成直接 Spring默认情况下只有一个线程来处理@Scheduled
那么如何让@Scheduled 多线程处理呢 可以用@Async
如果不用@Async呢
那么就给@Scheduled定义个线程池
@Scheduled的方法 不能有参数 不能有返回值
其他地方调用该方法
还可以使用ScheduledExecutorService Spring task底层用的ScheduledExecutorService
或者你也可以创建 ScheduledExecutorService
来调度
注意注意注意在不配置线程池的情况下 默认是单线程的