缓存流程

在讲这五个问题之前,首先我们回顾下正常的缓存的使用流程

程序在处理请求时,会先从缓存中进行查询,如果缓存中没有对应的key,则会从数据库中查询,如果查询到结果,并将查询结果添加到缓存中去,反之不缓存。流程就不多解释了,基于这个我们展开下面的问题。


缓存穿透

产生原因

当查询一个一定不存在的key时,由于不能命中缓存,所以要查询数据库,但是这个key又不存在,所以查询不到结果,不会缓存。于是就有了利用这种一定不存在的key作为查询条件,对系统进行攻击,增加数据库压力,这种现象称为缓存穿透

解决方法

  1. 布隆过滤
    首先要规范key的命名,对不规范的key直接过滤掉,并对所有可能的key以hash形式存储到一个足够大的bitmap中,不存在的数据会被此bitmap拦截,以避免查询数据库。
  2. 缓存空对象
    意思很简单,就是对返回数据为空的情况也进行缓存,并设置一个很短的过期时间,这样也能起缓解作用。但是这也会产生下面两个问题:

    • 缓存空对象意味着需要更多的存储空间,可再缩短缓存时间,过期自动剔除
    • 导致缓存与数据库不一致,比如某个key:a查询时还没有数据,这时会缓存空值,但是其他某个流程已走完,数据已添加到了数据库中,这时访问依旧会返回空值,因为缓存还没过期,所以解决方法就是增删改时也进行缓存的刷新

缓存雪崩

产生原因

当大批量缓存集中在同一时间内失效(或者redis宕机),产生大量缓存穿透,此时又有请求并发袭来,查询压力瞬间都落在了数据库上,此时就产生了缓存雪崩

解决方法

  1. 失效时间加随机值
    给缓存失效时间加一个随机值,避免集体失效
  2. 实现redis高可用
    通过对redis实现集群搭建来避免部分机器宕机导致redis不可用的情况
  3. 分布式锁或分布式队列
    保证缓存单线程写,并在没有获取锁的线程中一直轮询缓存,直到超时

缓存击穿

产生原因

缓存击穿是指缓存中没有但是数据库中有的数据(通常是缓存到期),由于并发,未能从缓存读到数据,从而引起数据库鸭梨瞬间增大

解决方法

  1. 设置热门缓存数据永不过期
    这里永不过期有两层意思:

    • 不设置过期时间或超长缓存时间即物理上不过期
    • 在缓存对象上添加一个标识过期时间的属性,在获取数据后校验过期时间,如果已过期则异步去更新改缓存
      这种方式可能会出现数据脏读(在缓存更新期间取到旧数据)的情况,视业务而定使用与否
  2. 分布式锁或分布式队列
    保证缓存单线程写,并在没有获取锁的线程中一直轮询缓存,直到超时

缓存一致性

如果对数据有强一致性要求的,那就不要使用缓存了


缓存并发竞争

产生原因

多个子系统set同一个key,导致产生并发竞争

解决方法

  1. 对key没有顺序要求
    使用分布式锁实现
  2. 对key有顺序要求
    将key对应的值带上时间戳
  3. 异步队列
    放入队列中,串行set就行

Redis-缓存穿透、缓存雪崩、缓存击穿、缓存一致性、并发竞争的更多相关文章

  1. Redis缓存穿透和雪崩

    缓存穿透 用户想要查询一个数据 在redis缓存数据库中没有获取到 就会向后端的数据库中查询. 当用户很多 都去访问后端数据库的话,这就会给数据库带来很大的压力. 常见场景:秒杀活动 等 解决方法: ...

  2. 缓存穿透、雪崩、热点与Redis

    (拼多多问:Redis雪崩解决办法) 导读:互联网系统中不可避免要大量用到缓存,在缓存的使用过程中,架构师需要注意哪些问题?本文以 Redis 为例,详细探讨了最关键的 3 个问题. 一.缓存穿透预防 ...

  3. Redis系列(八)--缓存穿透、雪崩、更新策略

    1.缓存更新策略 1.LRU/LFU/FIFO算法剔除:例如maxmemory-policy 2.超时剔除,过期时间expire,对于一些用户可以容忍延时更新的数据,例如文章简介内容改了几个字 3.主 ...

  4. redis的穿透和雪崩

    穿透: 从缓存中查询一个数据,查到为空,需要每次都去数据库中查询.而从数据库中查询出来也为空,也就不写入缓存.导致一个不存在的数每次都去数据库中查询,造成db系统很大压力 造成缓存穿透 解决:如果从数 ...

  5. 深入了解Redis(7)-缓存穿透,雪崩,击穿

    redis作为一个内存数据库,在生产环境中使用会遇到许多问题,特别是像电商系统用来存储热点数据,容易出现缓存穿透,雪崩,击穿等问题.所以实际运用中需要做好前期处理工作. 一.缓存雪崩 1.概念 缓存雪 ...

  6. Redis缓存雪崩、缓存穿透、缓存击穿、缓存降级、缓存预热、缓存更新

    Redis缓存能够有效地加速应用的读写速度,就DB来说,Redis成绩已经很惊人了,且不说memcachedb和Tokyo Cabinet之流,就说原版的memcached,速度似乎也只能达到这个级别 ...

  7. Redis高级应用解析:缓存穿透、击穿、雪崩

    1 背景 像我们去面试一些大公司的时候,就会遇到一些关于缓存的问题.可能很多同学都是接触过,多多少少了解一些,但是如果没有好好记录这些内容,不熟练精通的话,在真正面试的时候,就很难答出来了. 在我们的 ...

  8. SpringBoot微服务电商项目开发实战 --- Redis缓存雪崩、缓存穿透、缓存击穿防范

    最近已经推出了好几篇SpringBoot+Dubbo+Redis+Kafka实现电商的文章,今天再次回到分布式微服务项目中来,在开始写今天的系列五文章之前,我先回顾下前面的内容. 系列(一):主要说了 ...

  9. Redis中几个简单的概念:缓存穿透/击穿/雪崩,别再被吓唬了

    Redis中几个“看似”高大上的概念,经常有人提到,某些好事者喜欢死扣概念,实战没多少,嘴巴里冒出来的全是高大上的名词,个人一向鄙视概念党,呵呵! 其实这几个概念:缓存穿透/缓存击穿/缓存雪崩,有一个 ...

  10. Redis缓存穿透,缓存击穿,缓存雪崩,热点Key

    导读 使用Redis难免会遇到Redis缓存穿透,缓存击穿,缓存雪崩,热点Key的问题.有些同学可能只是会用Redis来存取,基本都是用项目里封装的工具类来操作.但是作为开发,我们使用Redis时可能 ...

随机推荐

  1. vector容器、

    一.  vector  向量容器1. 创建   vector  对象(1)不指定容器大小vector<int> V;(2)指定容器大小vector<int> V(10);(3) ...

  2. Django入门1--Django是什么?Django里文件的作用?

    Django项目目录介绍: wsgi.py文件介绍: urls.py文件介绍: __init__.py文件介绍:

  3. php_sphinx安装使用

    Sphinx的简介: Sphinx是一个独立的全文索引引擎,意图为其他应用提供高速.低空间 占用.搜索结果高相关度的全文搜索功能.Sphinx可以非常容易的与 SQL数据库和脚本语言集成.内置MySQ ...

  4. cfp大纲

    AFP基础知识 本章共14个考点,考试考15分左右. 本章重点: .职业道德准则 .家庭财务分析:净值的计算.储蓄的计算 .简单的财务比率分析 .金融理财和法律:企业组织形式.夫妻公共财产制度.财产分 ...

  5. es6—变量的解构赋值

    数组的解构赋值 ]]]]]]] = []}} = {}} = {}})]: first]: last} = arr} = {}) {}))}))}) {}))}))].]]]])})] }}} = { ...

  6. P1046 阶乘

    题目描述 给你一个数N,求 \(N!\) (即:N的阶乘).\(N! = N \times (N-1) \times \dots \times 2 \times 1\) 输入格式 输入一个整数 \(N ...

  7. dotnet core 使用 CoreRT 将程序编译为 Native 程序

    现在微软有一个开源项目 CoreRT 能通过将托管的 .NET Core 编译为单个无依赖的 Native 程序 这个项目现在还没发布,但是能尝试使用,可以带来很多的性能提升 使用 CoreRT 发布 ...

  8. 【t091】油滴扩展

    Time Limit: 1 second Memory Limit: 128 MB [问题描述] 在一个长方形框子里,最多有N(0≤N≤6)个相异的点.在其中任何一个点上放一个很小的油滴,那么这个油滴 ...

  9. 2018-10-19-C#-AddRange-添加位置

    title author date CreateTime categories C# AddRange 添加位置 lindexi 2018-10-19 9:3:8 +0800 2018-2-13 17 ...

  10. 【38.63%】【hdu 3047】Zjnu Stadium

    Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submission(s) ...