目录
步骤1:任务队列
package xiancheng.xianchengchi;
import java.util.ArrayDeque;
import java.util.Deque;
import java.util.Queue;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;
public class BlockingQueue<T> {
//任务队列
private Deque<T> queue = new ArrayDeque<>();
//锁
ReentrantLock lock = new ReentrantLock();
//生产者生产任务太多,线程处理不了,队列放不下时,阻塞到这个条件变量中
private Condition fullWaitSet = lock.newCondition();
//没有任务,消费者阻塞到这个条件变量
private Condition emptyWaitSet = lock.newCondition();
//任务队列容量
private int capcity;
public BlockingQueue(int capcity) {
this.capcity = capcity;
}
//消费者获取任务
public T poll(){
lock.lock();
try{
while(queue.isEmpty()){
//任务空,阻塞
emptyWaitSet.await();
}
//拿出任务,唤醒生产者继续生产
T t = queue.removeFirst();
fullWaitSet.signal();
return t;
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
lock.unlock();
}
return null;
}
//生产者添加任务
public void put(T task){
lock.lock();
try{
while (queue.size() == capcity) {
try {
//任务队列满了,生产者阻塞
fullWaitSet.await();
} catch (InterruptedException e) {
e.printStackTrace(); }
}
//生产出任务,添加到队列,唤醒消费者 消费
queue.addLast(task);
emptyWaitSet.signal();
}finally {
lock.unlock();
}
}
//队列中任务数量
public int size() { lock.lock();
try {
return queue.size();
} finally { lock.unlock();
}
}
}
步骤2:线程池
package xiancheng.xianchengchi;
import java.util.HashSet;
public class XianChengChi {
//任务队列
private BlockingQueue<Runnable> taskQueue;
//线程集合
private HashSet<Worker> workers = new HashSet<>();
//线程数量
private int coreSize;
//private RejectPolicy<Runnable> rejectPolicy;
public XianChengChi(int coreSize, int queueCapcity) {
this.coreSize = coreSize;
this.taskQueue = new BlockingQueue<>(queueCapcity);
//this.rejectPolicy = rejectPolicy;
}
//线程集合中的线程
class Worker extends Thread{
//线程中的任务
private Runnable task;
public Worker(Runnable task) {
this.task = task;
}
@Override
public void run() {
while(task != null || (task = taskQueue.poll()) != null) {
task.run();
}
synchronized (workers) {
workers.remove(this);
}
}
}
//执行任务
public void execute(Runnable task){
synchronized (workers) {
//如果线程数量没有超过限制,就产生一个线程去处理任务
if(workers.size() < coreSize) {
Worker worker = new Worker(task);
workers.add(worker);
worker.start();
}else{
//否则放进任务队列
taskQueue.put(task);
}
}
}
}
步骤3:测试
package xiancheng.xianchengchi;
public class TestXianchengchi {
public static void main(String[] args) {
XianChengChi xianChengChi = new XianChengChi(2, 4);
xianChengChi.execute(new Runnable() {
@Override
public void run() {
System.out.println("任务开始执行");
}
});
}
}