定时器的实现方式
-
数据结构出发
红黑树,最小堆,时间轮,跳表
4.分布式场景下:定时器设计
-
应用场景出发
单线程,多线程,分布式场景
定时器定位;服务器是怎么驱动逻辑的?
网络事件、定时事件、信号事件
怎么实现定时器?
单线程环境下: 通常与网络事件协调处理;
多线程环境下: 单独的定时器进行处理定时事件;
源码:
- redis:单线程,通常与网络事件(搜epoll_wait)协调处理
有很多离散的定时事件,拿最近要触发的定时任务,作为epoll_wait网络事件阻塞的时长
取最近要触发的定时任务
-
nginx:多进程,单线程---红黑树
红黑树是平衡二叉搜索树,返回树的最左边的叶子节点,就是最小值
-
skynet:多线程---时间轮/跳表
跳表是一个多层级链表,空间换时间,实现二分搜索
跳表通过加锁的方式,提供并发读写
时间轮(linux的定时器也是这个)
不需要维护整个数据结构,只要加到对应时间刻度的链表上(插入o(1))
并且对应的锁粒度也小,只要对某个时间刻度加锁,多线程性能高效
数组(时间轮)的大小必须大于 支持的最大的定时任务
但是又会出现空推进的问题
---所以要增加层级(拆分的思维)(秒层级,分层级,时层级)
分针移动一格:将此分针指向的任务链表进行重新映射到上一层级(上图是秒层级)
分布式场景:
1不能成为系统的风险点
2持久化 强一致性
3确保消费者正确消费 事务
必要性:
没有定时器,删除一个订单则要全表扫描,效率非常低。
如果有定时器就有订单id,可以直接删除,效率高
(分布式这里只是简单讲解)
https://www.bilibili.com/video/BV1uZ4y1r7Fy
(补充知识:
redis
内存 红黑树、跳表---红黑树锁的粒度太大了。要对整棵树加锁
磁盘 lsm tree、B+
)
(kv数据库:lsm-arrary、hashmap、跳表)
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享4款.NET开源、免费、实用的商城系统
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
· 上周热点回顾(2.24-3.2)