消息队列高手课
李玥
美团高级技术专家
52199 人已学习
新⼈⾸单¥59
登录后,你可以任选4讲全文学习
课程目录
已完结/共 42 讲
进阶篇 (21讲)
消息队列高手课
15
15
1.0x
00:00/00:00
登录|注册

16 | 缓存策略:如何使用缓存来减少磁盘IO?

LRU算法
最优的置换策略
设置过期时间
定时同步缓存
异步更新
同步更新
实现简单
适用范围更广
不推荐使用
非可靠的设计
缓存置换
选择缓存的数据
缓存命中率
更新缓存的方法
数据一致性问题
只读缓存
读写缓存
缓存置换策略
保持缓存数据新鲜
选择只读缓存还是读写缓存
使用@Cacheable注解来简单使用缓存
将低速存储的数据复制到高速存储中
实现一个采用LRU置换算法的缓存
提高缓存的命中率
缓存的思想
使用内存作为缓存来加速应用程序的访问速度
磁盘的读写速度较慢
服务器使用多块磁盘组成磁盘阵列
磁盘的持久化存储
现代消息队列使用磁盘文件存储消息
使用缓存来减少磁盘IO
思考题
缓存策略
缓存策略

该思维导图由 AI 生成,仅供参考

你好,我是李玥。这节课,我们一起来聊一聊缓存策略。
现代的消息队列,都使用磁盘文件来存储消息。因为磁盘是一个持久化的存储,即使服务器掉电也不会丢失数据。绝大多数用于生产系统的服务器,都会使用多块儿磁盘组成磁盘阵列,这样不仅服务器掉电不会丢失数据,即使其中的一块儿磁盘发生故障,也可以把数据从其他磁盘中恢复出来。
使用磁盘的另外一个原因是,磁盘很便宜,这样我们就可以用比较低的成本,来存储海量的消息。所以,不仅仅是消息队列,几乎所有的存储系统的数据,都需要保存到磁盘上。
但是,磁盘它有一个致命的问题,就是读写速度很慢。它有多慢呢?一般来说 SSD(固态硬盘)每秒钟可以读写几千次,如果说我们的程序在处理业务请求的时候直接来读写磁盘,假设处理每次请求需要读写 3~5 次,即使每次请求的数据量不大,你的程序最多每秒也就能处理 1000 次左右的请求。
而内存的随机读写速度是磁盘的 10 万倍!所以,使用内存作为缓存来加速应用程序的访问速度,是几乎所有高性能系统都会采用的方法。
缓存的思想很简单,就是把低速存储的数据,复制一份副本放到高速的存储中,用来加速数据的访问。缓存使用起来也非常简单,很多同学在做一些业务系统的时候,在一些执行比较慢的方法上加上一个 @Cacheable 的注解,就可以使用缓存来提升它的访问性能了。
确认放弃笔记?
放弃后所记笔记将不保留。
新功能上线,你的历史笔记已初始化为私密笔记,是否一键批量公开?
批量公开的笔记不会为你同步至部落
公开
同步至部落
取消
完成
0/2000
荧光笔
直线
曲线
笔记
复制
AI
  • 深入了解
  • 翻译
    • 英语
    • 中文简体
    • 中文繁体
    • 法语
    • 德语
    • 日语
    • 韩语
    • 俄语
    • 西班牙语
    • 阿拉伯语
  • 解释
  • 总结

现代高性能系统中,缓存是不可或缺的组成部分。缓存设计需要考虑数据一致性和命中率等问题。对于只读缓存,更新策略可以选择同步更新、定时全量更新或设置数据过期时间。在缓存置换策略方面,根据业务需求定制化策略是最佳选择,同时通用的LRU算法也是一个不错的选择。总的来说,只读缓存适用范围广,实现简单,而缓存更新和置换策略需要根据具体业务需求进行选择和设计。文章深入探讨了缓存策略的选择和设计,为读者提供了缓存策略的技术特点和应用指导。 文章标题:现代高性能系统中的缓存策略选择与设计 现代高性能系统中,缓存是必不可少的组成部分。缓存的设计需要考虑数据一致性和命中率等问题。对于只读缓存,更新策略可以选择同步更新、定时全量更新或设置数据过期时间。而在缓存置换策略方面,根据业务需求定制化策略是最佳选择,同时通用的LRU算法也是一个不错的选择。总的来说,只读缓存适用范围广,实现简单,而缓存更新和置换策略需要根据具体业务需求进行选择和设计。文章深入探讨了缓存策略的选择和设计,为读者提供了缓存策略的技术特点和应用指导。

仅可试看部分内容,如需阅读全部内容,请付费购买文章所属专栏
《消息队列高手课》
新⼈⾸单¥59
立即购买
登录 后留言

全部留言(47)

  • 最新
  • 精选
  • 大白给小白讲故事
    ”⻚⾯位置与尾部的距离。因为越是靠近尾部的数据,被访问的概率越⼤“ 不大理解这句话,尾部指的是啥?当某个客户端正在从很旧的位置开始向后读取⼀批历史数据,是怎么判断与尾部的距离,从而减少这部分的缓存。

    作者回复: 与尾部的距离=最后一个一条消息的尾部位置 - 页面的位置 这个值越小,说明请求的数据与尾部越近,置换的时候被留下的概率也就越大。 对于历史数据,由于距离远,这个值会很大,那这些页面在置换的时候被留下的概率就很小,所以很快就会被从内从中置换出去。

    2019-08-29
    18
  • Yasir
    交作业,双向链表实现 https://github.com/tuhao/leetcode/blob/master/src/mqexercise/LRUTest.java

    作者回复: 👍👍👍

    2019-11-07
    2
    9
  • 文中说SSD硬盘的访问速度每秒几千次,内存是硬盘的10万倍,那就是亿这个数量级了,运行那么快呢?CPU的缓存假如说是内存的千倍那就到了千亿的数据级了,会有那么快吗?

    作者回复: 这个是理论上的数据,实际上取决于随机顺序读写还是顺序读写,读写数据大小,差别还是非常大的。像CPU和内存,他们标称的速度都是多少多少Hz,这个赫兹Hz的意思就是每秒钟多少次,其实就是它的极限tps。 但实际我们执行一次数据读写或者一行代码,编译成CPU指令可能是几条指令,这样你就大概能推断出这条指令的执行速度应该是个什么量级的了。

    2019-08-29
    8
  • fomy
    老师,我在github上写了一个lru的实现。https://github.com/fomeiherz/code-snippet/tree/master/lru 使用了HashMap和Queue一起实现的。使用HashMap保存键值对可以实现O(1)复杂查询,使用队列保存key,头部出队,尾部入队。更新比较复杂,需要删除对应的元素后,才可以再入队,这里是O(n) 复杂度。 老师,更新队列顺序时是否会有更快办法?或者有更快的实现办法呢?求指导

    作者回复: 你这个实现中,命中缓存后“移动元素到尾部”这个操作,同时会移动其它无关的元素的位置(从队头移到队尾),这样就不满足LRU的原则了,可以试试将队列换成链表这种可以支持随机写的数据结构。

    2019-11-28
    5
  • 13761642169
    PageCache是OS提供的能力,用户程序调用什么API才能使用到PageCache,为什么说kafka大量使用到PageCache,因为mmap?

    作者回复: 对应的几个写文件的系统调用都会经过PageCache,比如write pwrite还有mmap

    2019-09-22
    3
  • A9
    JMQ是如何使用自定义的LRU算法的?即使使用DirectBuffer不是也要经过PageCache吗?

    作者回复: DirectBuffer确实也需要经过PageCache,但是它有更好的批量大小,写入时的系统调用次数也会更少,所以性能更好一些。

    2019-10-27
    2
  • 约书亚
    来晚了,根据jms和kafka这两节,我试着猜想一下jms的机制,顺便提个问题: 1. 老师这节提到的jms实现的缓存机制,都是基于direct buffer自己实现的一个内存池,并实现了变种的LRU对么?这个缓存就是前面提到的journal cache,被writeThread/RelicationThread/FlushThread使用? 2. 这个内存池看起来并没有借助于netty的direict buffer pool是吧? 3. 那原谅我对比一下jms和rocket,jms没有基于mmap去做而选择direct buffer,看起来是为了: a. 减少GC的压力 b. 比mmap更容易控制,就更容增加缓存的命中率 这样? 4. 另外,有个概念我很模糊,有资料说direct buffer在写磁盘/socket时并不能真的节省一次cpu copy?那这样的话jms可以说并没有利用zero copy? 望解惑

    作者回复: A1:是的。 A2:是的。 对于问题3和4,你可以看一下关于JMQ的这篇文章: https://www.jiqizhixin.com/articles/2019-01-21-19

    2019-09-01
    2
  • 77
    老师问个问题,关于读写缓存和只读缓存第一种的区别是不是 读写缓存是更新缓存然后异步去更新磁盘文件,只读缓存是先更新磁盘在更新缓存呢?

    作者回复: 读写缓存和只读缓存的区别是,数据在更新的时候,是否去更新缓存。 至于是先更新缓存,还是先更新磁盘文件,这个取决于不同的缓存策略。

    2020-04-29
    1
  • 明日
    Java实现: https://gist.github.com/imgaoxin/ed59397c895b5a8a9572408b98542015

    作者回复: 👍👍👍

    2019-09-03
    3
  • humor
    我感觉读写缓存和只读缓存的第一种更新策略(更新数据的同时更新缓存)是一样的吧?因为它们都需要同时更新数据和缓存,区别可能是读写缓存以更新缓存为主,只读缓存的第一种更新策略是以更新数据为主吗

    作者回复: 还有就是,读写缓存可以为写入加速,但牺牲了数据可靠性。

    2019-08-30
收起评论
显示
设置
留言
47
收藏
沉浸
阅读
分享
手机端
快捷键
回顶部