Caused by: java.lang.IllegalArgumentException: null
at java.base/java.util.concurrent.ThreadPoolExecutor.<init>(ThreadPoolExecutor.java:1293) ~[na:na]
......
遇到了这么一个神奇的错误 非法参数异常 ,而且是在创建线程池的时候触发的. 创建线程池的参数如下,可见每个参数都有显式的值.最主要的是在本地运行是正常的,问题出在哪里呢? 先给出结论: 核心线程池大小大于了最大线程池大小.
private static final ThreadPoolExecutor POOL_EXECUTOR = new ThreadPoolExecutor(3, Runtime.getRuntime().availableProcessors(), 30, TimeUnit.SECONDS, new LinkedBlockingDeque<>(), Executors.defaultThreadFactory(), new ThreadPoolExecutor.CallerRunsPolicy());
让我们点开源码看一下:
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory,
RejectedExecutionHandler handler) {
if (corePoolSize < 0 ||
maximumPoolSize <= 0 ||
maximumPoolSize < corePoolSize ||
keepAliveTime < 0)
throw new IllegalArgumentException();
确实在创建线程池的时候有可能抛出 非法参数异常. 对比下这几条异常条件 corePoolSize < 0 不满足,默认线程池大小为 3 , keepAliveTime < 0 不满足,这里为30秒. 那么剩下的只有 maximumPoolSize <= 0 和 maximumPoolSize < corePoolSize 这两个了. Runtime.getRuntime().availableProcessors()点进去瞅一眼,是个native方法,返回值永远 ,那么
maximumPoolSize <= 0自然也不满足了.
maximumPoolSize < corePoolSize 这一条了......这时候我才想起我只有一台一核2G的云主机,开发机有16个框框自然不会报错了.
google一下遇到这个问题的人还挺多的,似乎只能尽量避免这种代码了. 或者将最大线程数目写死? 似乎并没有两全其美的办法.