java线程池的实现(原理)

我们并不是要闭门造车,因为现在市面上有一些非常优秀的线程池供我们使用,我们写这段代码的目的是为了更好的理解和使用线程池。

首先说一说一个线程池应该具备哪些东西

1 初始化线程个数

2核心线程个数

3最大线程个数

4任务添加策略

5任务队列

6线程的构造工厂

我们有这些基本就算是够了

现在我们先来定义接口

/**
 * 线程池的接口
 * @author 魏金浩
 *
 */
public interface ThreadPool {
	/*
	 * 提交任务到线程池
	 */
	public void execute(Runnable runnable) throws Exception;
	/**
	 * 关闭线程池
	 */
	public void shutdown();
	/**
	 * 判断当前线程池是否被关闭
	 * @return 线程池的关闭状态
	 */
	public boolean isShutdown();
	/**
	 * 获取线程池的最大数
	 * @return 线程池的最大数
	 */
	public int getMaxSize();
	/**
	 * 获取线程池的初始化大小
	 * @return 线程池的初始化大小
	 */
	public int getInitSize();
	/**
	 * 获取线程池的核心线程数
	 * @return 获取线程池的核心线程数
	 */
	public int getCoreSize();
	/**
	 * 获取线程池的活跃线程数
	 * @return 获取线程池的活跃线程数
	 */
	public int getActiveSize();
	
	/**
	 * 获取任务队列的大小
	 * @return 任务队列的大小
	 */
	public int getQueueSize();
	
}
/**
 * 构造线程的工厂
 * @author 魏金浩
 *
 */
public interface ThreadFactory {
	/**
	 * 根据runnable去创建线程
	 * @param runnable 根据他去创建线程 
	 * @return 创建的线程
	 */
	Thread createThread(Runnable runnable);
}
/**
 * 任务队列
 * @author 魏金浩
 *
 */
public interface RunnableQueue {
	/**
	 * 将任务提交到任务队列中
	 * @param runnable 用户提交的任务
	 */
	public void offer(Runnable runnable);
	/**
	 * 供工作线程使用从队列中获取Runnable
	 * @return 从队列中获取Runnable
	 * @throws InterruptedException 
	 */
	public Runnable take() throws InterruptedException;
	/**
	 * 获取任务队列中任务的数量
	 * @return 任务队列中任务的数量
	 */
	public int size();
}
/**
 * 当任务队列满时的拒绝策略
 * @author 魏金浩
 *
 */
public interface DenyPolicy {
	
	public void reject(Runnable runnable ,ThreadPool pool);
	
	//该拒绝策略将会直接丢弃任务
	class DiscardDenyPolicy implements DenyPolicy {

		@Override
		public void reject(Runnable runnable, ThreadPool pool) {
			
		}
	}
	//该拒绝策略会抛出异常
	class AbortDenyPolicy implements DenyPolicy {

		@Override
		public void reject(Runnable runnable, ThreadPool pool) {
			throw new DenyRunnableException("the runnable" + runnable + "will be abort.");
		}
	}
	//该拒绝策略会在用户的工作线程中执行任务
	class RunnerDenyPolicy implements DenyPolicy {

		@Override
		public void reject(Runnable runnable, ThreadPool pool) {
			if(pool.isShutdown() != true) {
				runnable.run();
			}
		}
	}
}

上面的任务添加策略中我们在其内部实现了三个策略,详细的作用已经进行了标注

剩下的任务就是进行接口的实现了

任务队列的实现

public class LinkedRunnableQueue implements RunnableQueue{
	//任务添加策略
	private DenyPolicy denyPolicy;
	//存放任务的容器
	private LinkedList<Runnable> queue;
	//存放任务的最大个数
	private int limit;
	//供我们的任务添加策略使用
	private ThreadPool pool;
	
	public LinkedRunnableQueue(DenyPolicy denyPolicy ,int limit ,ThreadPool pool) {
		super();
		this.denyPolicy = denyPolicy;
		this.queue = new LinkedList<>();
		this.limit = limit;
		this.pool = pool;
	}

	@Override
	public void offer(Runnable runnable) {
		synchronized (queue) {
			if(queue.size() >= limit) {
				denyPolicy.reject(runnable, pool);
			}
			else {
				queue.addLast(runnable);
				queue.notifyAll();
				
			}
		}
	}

	@Override
	public Runnable take() throws InterruptedException {
		synchronized (queue) {
			while (queue.size() ==0) {
				try {
					queue.wait();
				} catch (InterruptedException e) {
					throw e;
				}
			}
			Runnable first = queue.removeFirst();
			return first;
		}
	}

	@Override
	public int size() {
		synchronized (queue) {
			return queue.size();
		}
	}

}

任务添加策略所需要的异常类

public class DenyRunnableException extends RuntimeException{
	
	public DenyRunnableException(String message) {
		super(message);
	}
}
/**
 * 用于线程池内部作用是去在任务队列中去任务
 * @author 魏金浩
 *
 */
public class InternalTask implements Runnable{
	
	private final RunnableQueue runnableQueue;
	
	private boolean running = true;
	
	public InternalTask(RunnableQueue runnableQueue) {
		this.runnableQueue = runnableQueue;
	}
	
	public void stop() {
		this.running = false;
	}
	//他的作用就是不断的从任务队列中进行取出,并执行任务的run方法
	@Override
	public void run() {
		while(running != false && Thread.currentThread().isInterrupted() != true) {
			try {
				Runnable runnable = runnableQueue.take();
				runnable.run();
			}catch ( InterruptedException e) {
				this.running = false;
				break;
			}
		}
	}
	
	
}
public class BaiscThreadPool extends Thread implements ThreadPool{
	
	private int maxSize;
	private int coreSize;
	private int initSize;
	private int activeAccount;
	private boolean shutdown = false;
	private RunnableQueue runnableQueue;
	private Queue<ThreadTask> queue;
	private DenyPolicy denyPolicy;
	private ThreadFactory threadFactory;
	private long keepAliveTime;
	private TimeUnit timeUnit;
	
	private static DenyPolicy DEFAULT_DENYPOLICY = new DenyPolicy.DiscardDenyPolicy();
	private static ThreadFactory DEFAULT_THREADFACTORY = new BaiscThreadPool.DefaultThreadFactory();
	
	
	public BaiscThreadPool(int maxSize, int coreSize, int initSize,int queueSize) {
		this(maxSize,coreSize,initSize,10,TimeUnit.SECONDS,queueSize);
	}
	
	private BaiscThreadPool(int maxSize, int coreSize, int initSize, 
			long keepAliveTime,TimeUnit timeUnit,int queueSize) {
		super();
		this.maxSize = maxSize;
		this.coreSize = coreSize;
		this.initSize = initSize;
		this.runnableQueue = new LinkedRunnableQueue(DEFAULT_DENYPOLICY,queueSize,this);
		this.queue = new ArrayDeque<>();
		this.keepAliveTime = keepAliveTime;
		this.timeUnit = timeUnit;
		this.threadFactory=this.DEFAULT_THREADFACTORY;
		this.init();
	}
	private void init() {
		start();
		
		for(int i = 0;i < this.initSize;i++) {
			newThread();
		}
		
	}
	private void newThread() {
		InternalTask internalTask = new InternalTask(this.runnableQueue);
		Thread thread = this.threadFactory.createThread(internalTask);
		ThreadTask threadTask = new ThreadTask(thread,internalTask);
		queue.offer(threadTask);
		this.activeAccount ++;
		thread.start();
	}
	
	private void removeThread() {
		ThreadTask threadTask = queue.remove();
		threadTask.internalTask.stop();
		this.activeAccount --;
	}
	
	@Override
	public void run() {
		
		while(this.shutdown != true && !this.isInterrupted()) {
				try {
					timeUnit.sleep(keepAliveTime);
				} catch (InterruptedException e) {
					this.shutdown = true;
					break;
				}
				synchronized (this) {
					if(this.shutdown) {
						break;
					}
					//当前任务中有任务没有处理,并且当前线程数没有达到核心线程数
					if(this.runnableQueue.size() >0 && this.activeAccount < this.coreSize) {
						for (int i = this.activeAccount; i < this.coreSize; i++) {
							newThread();
						}
						continue;
					}
					//当前任务中有任务没有处理,并且当前线程数没有达到上限
					if(this.runnableQueue.size() > 0 && this.activeAccount < this.maxSize) {
						for (int i = this.activeAccount; i < this.maxSize; i++) {
							newThread();
						}
					}
					
					//当前任务队列中没有任务要处理,进行线程的回收,回收到核心线程数即可
					if(this.runnableQueue.size() == 0 && this.activeAccount > this.coreSize) {
						for (int i = this.coreSize; i < this.activeAccount; i++) {
							removeThread();
						}
					}
				}
		}
	}
	
	@Override
	public void execute(Runnable runnable) throws Exception {
		if(this.shutdown ==false) {
			this.runnableQueue.offer(runnable);
		}else {
			throw new Exception("thread pool is destory.");
		}
		
	}

	@Override
	public void shutdown() {
		synchronized (this) {
			if(this.shutdown) {
				return ;
			}
			this.shutdown = true;
			this.queue.forEach((threadTask) -> {
				threadTask.internalTask.stop();
				threadTask.thread.interrupt();
			});
			this.interrupt();
		}
	}

	@Override
	public boolean isShutdown() {
		return this.shutdown;
	}

	@Override
	public int getMaxSize() {
		return this.maxSize;
	}

	@Override
	public int getInitSize() {
		return this.initSize;
	}

	@Override
	public int getCoreSize() {
		return this.coreSize;
	}

	@Override
	public int getActiveSize() {
		return this.activeAccount;
	}

	@Override
	public int getQueueSize() {
		return this.runnableQueue.size();
	}
	
	public  class ThreadTask {
		private Thread thread;
		private InternalTask internalTask;
		public ThreadTask(Thread thread, InternalTask internalTask) {
			super();
			this.thread = thread;
			this.internalTask = internalTask;
		}
		
	}
	
	static public class DefaultThreadFactory implements ThreadFactory{

		@Override
		public Thread createThread(Runnable runnable) {
			return new Thread(runnable);
		}
		
	}
}
标题

猜你喜欢

转载自blog.csdn.net/c1523456/article/details/81415759