并发Queue

Queue

在并发队列上JDK提供2套实现,一个是以ConcurrentLinkedQueue为代表的高性能队列,一个是以BlockingQueue接口为代表的阻塞队列,一个是以BlockingQueue接口为代表的阻塞队列,无论哪种都继承自Queue接口。

boolean add(E e)
将指定的元素插入此队列(如果立即可行且不会违反容量限制),在成功时返回 true,如果当前没有可用的空间,则抛出 IllegalStateException。

boolean offer(E e)
将指定的元素插入此队列(如果立即可行且不会违反容量限制),当使用有容量限制的队列时,此方法通常要优于 add(E),后者可能无法插入元素,而只是抛出一个异常。

remove()
 获取并移除此队列的头。此方法与 poll唯一的不同在于:此队列为空时将抛出一个异常。
poll()
  获取并移除此队列的头,如果此队列为空,则返回 null。
peek()
  获取但不移除此队列的头;如果此队列为空,则返回 null。

ConcurrentLinkedQueue类

是一个适用于高并发产经下的队列,通过无锁的方式,实现了高并发状态下的高性能,通常ConcurrentLinkedQueue性能好于BlockingQueue。他是一个机遇链接点的无界线程安全队列。

该队列是先进先出的原则,头是最先加入的,尾是最近加入的。该队列不允许NULL元素;

add()offer()都是加入元素,ConcurrentLinkedQueue中这两个方法都没有任何的区别;

poll()peek()都是取头元素节点,区别在于前者会删除元素,后者不会;

BlockingQueue接口

offer() 表示如果可能的话,将anObject加到BlockingQueuue里,即如果BlockingQueue可以容纳,则返回true,否者返回false.(本方法不阻塞当前执行的方法的线程)

offer(E O ,Long timeout,TimeUnit unit) 可以设定等待时间如果在指点的时间内还不能在队列之加入元素,则返回失败。

put(anObject) 把anObject加到BloclingQueue里,如果BlockQueue没有空间则调用此方法的线程被阻断直到BlockingQueue里面有空间再继续。

poll(long timeout,TimeUnit unit):从BlockingQueue取出一个队首的对象,如果在指定的时间内,队列一旦有数据可以取了则立即返回队列中的数据,否则知道时间超时还没有数据可以取的,返回失败。

take():取走BlockingQueue里排在首位的对象,若BlockingQueue为空,阻断进入等待状态的BlockingQueue有新的数据被加入。

drainTo():一次性从BlockingQueue获取所有可用的数据对象(还可以指定获取数据的个数),通过该方法,可以提升获取数据效率;不需要多次分批加锁或释放锁。

实现类

ArrayBlockingQueueDelayQueueLinkedBlockingDequeLinkedBlockingQueue

PriorityBlockingQueueSynchronousQueue

 

MyQueue

package com.infree.thread.core.collection;

import java.util.LinkedList;
import java.util.concurrent.atomic.AtomicInteger;

public class MyQueue {
	
	private final LinkedList<Object> linkedList = new LinkedList<>();
	
	private final AtomicInteger count = new AtomicInteger(0);
	private final int maxSize;
	private final int minSize = 0;
	private final Object lock = new Object();
	public MyQueue(int len) {
		this.maxSize = len;
	}
	
	public void put(Object obj){
		synchronized (lock) {
			while(count.get() == this.maxSize){
				try {
					lock.wait();
					
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
			// 添加新的元素到容器中
			linkedList.add(obj);
			count.getAndIncrement();  //i++
			lock.notify(); //唤醒线程
			
			
		}

	}
	
	public Object take(){
		Object item = null;
		synchronized (lock) {
			while(count.get()== this.minSize){
				try {
					lock.wait();
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
			}
			item = linkedList.removeFirst();
			count.getAndDecrement(); // i --
			lock.notify();//唤醒线程
		}
		
		return item;
	}
	
	public int size() {
		return linkedList.size();
	}
	
	public String getLinkListString() {
		return linkedList.toString();
	}
}
package com.infree.thread.core.collection;

public class MyQueueTest {
	
	public static void main(String[] args) throws InterruptedException {
		MyQueue myQueue = new MyQueue(5);
		myQueue.put("a");
		myQueue.put("b");
		myQueue.put("c");
		myQueue.put("d");
		myQueue.put("e");
		
		
		Thread thread1 = new Thread(new Runnable() {
			@Override
			public void run() {
				myQueue.put("f");
				myQueue.put("g");
			}
		},"线程一");
		
		Thread thread2 = new Thread(new Runnable() {
			
			@Override
			public void run() {
				myQueue.take();
				try {
					Thread.sleep(1000);
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
				myQueue.take();
			}
		},"线程2");
		thread1.start();
		Thread.sleep(1000);
		
		System.err.println(myQueue.size());
		
		thread2.start();
		
		Thread.sleep(5000);
		System.err.println(myQueue.getLinkListString());
	}
}

附加:ArraylistLinkedlist的区别

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值