自己動手寫執行緒池
阿新 • • 發佈:2019-05-31
自己動手寫執行緒池
執行緒池 = 有界/無界佇列<Runable> + List<Thread> + 飽和策略
import java.util.ArrayList; import java.util.concurrent.BlockingQueue; import java.util.concurrent.CountDownLatch; import java.util.concurrent.LinkedBlockingQueue; public class MyThreadPool { private BlockingQueue<Runnable> blockingQueue = null; private ArrayList<Thread> allThreads = null; private boolean isWorking = true; MyThreadPool(int poolSize,int queueSize){ blockingQueue = new LinkedBlockingQueue(queueSize); allThreads = new ArrayList<>(poolSize); for(int i = 0 ; i < poolSize; i++){ Worker thread = new Worker(this); allThreads.add(thread); thread.start(); } } private static class Worker extends Thread{ MyThreadPool pool; Worker(MyThreadPool pool){ this.pool = pool; } @Override public void run() { while (pool.isWorking || pool.blockingQueue.size() > 0) { try { Runnable runnable = pool.blockingQueue.take(); runnable.run(); } catch (InterruptedException e) { // e.printStackTrace(); } } } } public boolean subumit(Runnable runnable) throws InterruptedException { return blockingQueue.offer(runnable); } /**兩個問題: * 1.阻塞在take地方的怎麼把他停掉?InterruptedException * 2.保證已經在queue裡面的Runable要執行完成. pool.blockingQueue.size() > 0 */ public void shutDown(){ isWorking = false; for(Thread thread : allThreads){ thread.interrupt(); } } public static void main(String[] argv) throws InterruptedException { int threadCount = 100; CountDownLatch countDownLatch = new CountDownLatch(threadCount); MyThreadPool myThreadPool = new MyThreadPool(5,10); for(int i=0 ; i < threadCount; i++){ boolean isAccept = myThreadPool.subumit(new Runnable() { @Override public void run() { try { Thread.sleep(50); } catch (InterruptedException e) { // e.printStackTrace(); } System.out.println("thread " + Thread.currentThread().getName() + " run"); // countDownLatch.countDown(); } }); if(isAccept){ System.out.println("Thread " + i + "has been Submit"); } } // countDownLatch.await(); Thread.sleep(100); myThreadPool.shutDown(); } }
執行緒池被請求打滿的原因有兩個,一個是核心執行緒數太少,還有可能是執行緒runnable的任務耗時變長導致處理不過來。
解決方法一個是增大核心執行緒數;二是檢查是否run裡面有可以