缓存穿透、缓存雪崩、缓存击穿

缓存穿透
  • 缓存穿透是指查询一个一定不存在的数据。由于缓存命不中时会去查询数据库,查不到数据则不写入缓存,这将导致这个不存在的数据每次请求都要到数据库去查询,造成缓存穿透。
  • 解决方案:

    • 是将空对象也缓存起来,并给它设置一个很短的过期时间,最长不超过5分钟
    • 采用布隆过滤器,将所有可能存在的数据哈希到一个足够大的bitmap中,一个一定不存在的数据会被这个bitmap拦截掉,从而避免了对底层存储系统的查询压力
      缓存雪崩
  • 如果缓存集中在一段时间内失效,发生大量的缓存穿透,所有的查询都落在数据库上,就会造成缓存雪崩。

  • 解决方案:

    • 尽量让失效的时间点不分布在同一个时间点
      缓存击穿
  • 缓存击穿是指一个key非常热点,在不停的扛着大并发,当这个key在失效的瞬间,持续的大并发就穿破缓存,直接请求数据库,就像在一个屏障上凿开了一个洞。

  • 解决方案:

    • 可以设置key永不过期

      哨兵模式

  • 主从复制中反客为主的自动版,如果主机Down掉,哨兵会从从机中选择一台作为主机,并将它设置为其他从机的主机,而且如果原来的主机再次启动的话也会成为从机。

    数据类型

    | string | 字符串 | | —- | —- | | list | 可以重复的集合 | | set | 不可以重复的集合 | | hash | 类似于Map | | zset(sorted set) | 带分数的set |

持久化

RDB持久化:
  • 在指定的时间间隔内持久化
  • 服务shutdown会自动持久化
  • 输入bgsave也会持久化

    AOF : 以日志形式记录每个更新操作
  • Redis重新启动时读取这个文件,重新执行新建、修改数据的命令恢复数据。

    保存策略:
  • 推荐(并且也是默认)的措施为每秒持久化一次,这种策略可以兼顾速度和安全性。

  • 缺点:

    • 比起RDB占用更多的磁盘空间
    • 恢复备份速度要慢
    • 每次读写都同步的话,有一定的性能压力
    • 存在个别Bug,造成恢复不能
      选择策略:
  • 如果对数据不敏感,可以选单独用RDB;不建议单独用AOF,因为可能出现Bug;如果只是做纯内存缓存,可以都不用

    redis是单线程的,为什么那么快

  • 完全基于内存,绝大部分请求是纯粹的内存操作,非常快速。

  • 数据结构简单,对数据操作也简单,Redis中的数据结构是专门进行设计的
  • 采用单线程,避免了不必要的上下文切换和竞争条件,也不存在多进程或者多线程导致的切换而消耗 CPU,不用去考虑各种锁的问题,不存在加锁释放锁操作,没有因为可能出现死锁而导致的性能消耗
  • 使用多路I/O复用模型,非阻塞IO
  • 使用底层模型不同,它们之间底层实现方式以及与客户端之间通信的应用协议不一样,Redis直接自己构建了VM 机制 ,因为一般的系统调用系统函数的话,会浪费一定的时间去移动和请求