简介
原文介绍:
1 | An unbounded blocking queue of Delayed elements, in which an element can only be taken when its delay has expired. The head of the queue is that Delayed element whose delay expired furthest in the past. If no delay has expired there is no head and poll will return null. Expiration occurs when an element's getDelay(TimeUnit.NANOSECONDS) method returns a value less than or equal to zero. Even though unexpired elements cannot be removed using take or poll, they are otherwise treated as normal elements. For example, the size method returns the count of both expired and unexpired elements. This queue does not permit null elements. |
简单翻译
DelayQueue是一个无界阻塞队列,只有在延迟期满时,才能从中提取元素。
队列的头部,是延迟期满后保存时间最长的delay元素。
使用场景
订单定时取消,我们原来有这样一个需求:一个订单提交后在三十分钟内未支付就取消该订单。在订单少的时候采用的方法是一个定时调度任务每隔一分钟就扫描一次数据库(一分钟能接受),查找创建时间大于当前时间加三十分钟且未支付的订单,订单少任务还能处理,订单一旦多起来,有些订单的取消时间就不止三十分钟,这就不能接受了。尤其是在抢货时,延迟就更加严重。这时候DelayQueue就能排上用场
其他场景:定时调度,key失效(如缓存)
DelayQueue的使用条件
- 存放DelayQueue的元素,必须继承Delay接口,Delay接口使对象成为延迟对象。
1
2
3public class DelayQueue<E extends Delayed> extends AbstractQueue<E> implements BlockingQueue<E> {
} - 该接口强制实现两个方法:
1.CompareTo(Delayed o):用于比较延时,队列里元素的排序依据,这个是Comparable接口的方法,因为Delay实现了Comparable接口,所以需要实现。
2.getDelay(TimeUnit unit):这个接口返回到激活日期的–剩余时间,时间单位由单位参数指定。1
2
3
4
5
6public interface Delayed extends Comparable<Delayed> {
/**
* 剩余时间,小于等于0就表示该元素已过时
*/
long getDelay(TimeUnit unit);
} - 队列中不允许使用null元素。
代码示例
1 | package io.github.mylyed.h1.base; |
部分运行结果
1 | 23:52:08.795 [main] DEBUG i.g.mylyed.h1.base.DelayedQueneTest - start time:2020-04-08T23:52:08.784 |
源码详解
TODO
题外话
说来惭愧,许久没有写点东西了。