正確關(guān)閉線程池:shutdown 和 shutdownNow 的區(qū)別
點(diǎn)擊上方藍(lán)色字體,選擇“標(biāo)星公眾號(hào)”
優(yōu)質(zhì)文章,第一時(shí)間送達(dá)
前言
項(xiàng)目環(huán)境
1.線程池示例
public class ShutDownThreadPoolDemo {
private ExecutorService service = Executors.newFixedThreadPool(10);
public static void main(String[] args) {
new ShutDownThreadPoolDemo().executeTask();
}
public void executeTask() {
for (int i = 0; i < 100; i++) {
service.submit(() -> {
System.out.println(Thread.currentThread().getName() + "->執(zhí)行");
});
}
}
}
pool-1-thread-2->執(zhí)行
pool-1-thread-3->執(zhí)行
pool-1-thread-1->執(zhí)行
pool-1-thread-4->執(zhí)行
pool-1-thread-5->執(zhí)行
pool-1-thread-6->執(zhí)行
...
2.shutdown
public void execute(Runnable command) {
if (command == null)
throw new NullPointerException();
int c = ctl.get();
// 線程池中的線程比核心線程數(shù)少
if (workerCountOf(c) < corePoolSize) {
// 新建一個(gè)核心線程執(zhí)行任務(wù)
if (addWorker(command, true))
return;
c = ctl.get();
}
// 核心線程已滿,但是任務(wù)隊(duì)列未滿,添加到隊(duì)列中
if (isRunning(c) && workQueue.offer(command)) {
int recheck = ctl.get();
// 任務(wù)成功添加到隊(duì)列以后,再次檢查是否需要添加新的線程,因?yàn)橐汛嬖诘木€程可能被銷毀了
if (! isRunning(recheck) && remove(command))
// 如果線程池處于非運(yùn)行狀態(tài),并且把當(dāng)前的任務(wù)從任務(wù)隊(duì)列中移除成功,則拒絕該任務(wù)
reject(command);
else if (workerCountOf(recheck) == 0)
// 如果之前的線程已經(jīng)被銷毀完,新建一個(gè)非核心線程
addWorker(null, false);
}
// 核心線程池已滿,隊(duì)列已滿,嘗試創(chuàng)建一個(gè)非核心新的線程
else if (!addWorker(command, false))
// 如果創(chuàng)建新線程失敗,說明線程池關(guān)閉或者線程池滿了,拒絕任務(wù)
reject(command);
}
3.isShutdown
4.isTerminated
5.awaitTermination
6.shutdownNow
public List<Runnable> shutdownNow() {
List<Runnable> tasks;
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
checkShutdownAccess();
advanceRunState(STOP);
interruptWorkers();
tasks = drainQueue();
} finally {
mainLock.unlock();
}
tryTerminate();
return tasks;
}
7.shutdown 和 shutdownNow 的區(qū)別?
作者 | 不懂的浪漫
來源 | csdn.net/xiewenfeng520/article/details/107013342

評(píng)論
圖片
表情
