业务背景
在平时的业务中我们可能会碰到这样的需求,用户A将任务分配给用户B,如果30天后用户B还没有处理这个任务,那么系统自动将这个任务转发给用户C,或者将任务退回给任务A。
这里我们就可以使用延迟队列,我们写好转发方法或者退回方法,用户A分配任务时将时间记录放入延迟队列。当30天后用户B没有处理,我们获取从延迟队列里面获取这个记录,能获取得到,就执行转发方法或退回方法。如果30天内用户B处理了任务,那么就将延迟队列对应的时间记录删掉。
任务转办
当然延迟队列还有很多使用场景,比如用户下单30分钟还没付款,就将订单关闭、外卖平台发送订餐通知,下单成功后60s给用户推送短信等。
Redis实现的延迟队列
我们可以使用Redis的zset
可以用于作延迟队列,score
为延迟的时间点,获取时顺序获取端口的值,如果当前时间戳等于score
则可取出。
至于如何使用Redis做延迟队列,有兴趣的童鞋可以看看我之前下的这篇文章:
“[Redis实现延迟队列](Redis实现延迟队列 (qq.com))
”
Java自带的延迟队列
当然使用Redis做延迟队列并投入生产,其设计还是很复杂的,这里我推荐JDK中的延迟队列API,在java.util.concurrent
包下DelayQueue
。
我们来看看它的使用。
首先我们直接创建一个延迟队列:
// 延迟消息队列
private static DelayQueue delayQueue = new DelayQueue();
系统启动后,我们先后添加两个消息:
public static void producer() {
// 添加消息
delayQueue.put(new MyDelay(1000, "消息1"));
delayQueue.put(new MyDelay(3000, "消息2"));
}
我们再来从延迟队列中获取数据:
public static void consumer() throws InterruptedException {
System.out.println("开始执行时间:" +
DateFormat.getDateTimeInstance().format(new Date()));
while (!delayQueue.isEmpty()) {
System.out.println(delayQueue.take());
}
System.out.println("结束执行时间:" +
DateFormat.getDateTimeInstance().format(new Date()));
}
测试结果为:
开始执行时间:2020-12-5 13:50:34
消息1
消息2
结束执行时间:2020-12-5 13:50:37
我们看到,消息2在延迟了3s后才从队列中被取出。
关于DelayQueue
实际是基于优先队列来实现的。所谓的优先队列,出队是按照优先级来出的,并不是像传统的队列那样先进先出。优先队列底层是二叉堆,关于什么是二叉堆,有兴趣的童鞋可以去网上了解下。
下面是优先队列的示例代码:
实体Student
的值:
@AllArgsConstructor
@Data
public class Student {
private Integer score;
private String name;
...
}
这里我们按照score
值从大到小出队。
代码执行结果:
Name:Zhouzhou Level:100
Name:Lvshen Level:80
Name:Hall Level:60
关于其它的方式实现延迟队列
我在网上收集了几种延迟队列的实现方式:
“”
定期轮询(数据库等)
DelayQueue(JDK的API)
Timer
ScheduledExecutorService
时间轮(kafka)
RabbitMQ
Quartz
Redis Zset
Koala
JCronTab
SchedulerX(阿里)
有赞延迟队列
具体实现方式可以看看这篇文章:
“你真的了解延时队列吗
”
好啦今天的文章就到这里啦!如果你的项目中有需要使用延迟队列的地方,希望这篇文章能帮助你。
往期推荐
扫码二维码,获取更多精彩。或微信搜Lvshen_9,可后台回复获取资料
回复"java" 获取java电子书;
回复"python"获取python电子书;
回复"算法"获取算法电子书;
回复"大数据"获取大数据电子书;
回复"spring"获取SpringBoot的学习视频。
回复"面试"获取一线大厂面试资料
回复"进阶之路"获取Java进阶之路的思维导图
回复"手册"获取阿里巴巴Java开发手册(嵩山终极版)
回复"总结"获取Java后端面试经验总结PDF版
回复"Redis"获取Redis命令手册,和Redis专项面试习题(PDF)
回复"并发导图"获取Java并发编程思维导图(xmind终极版)
另:点击【我的福利】有更多惊喜哦。