Redis 的key设计技巧

1.1 原主键列进行查询

比照关系数据库的设计:
1): 把表名转换为key前缀.
2): 第2段放置用于区分区key的字段–对应mysql中的主键的列名,如userid
3): 第3段放置主键值,如2,3,4…., a , b ,c
4): 第4段,写要存储的列名

对该表设置redis的key如下设计:

1.2原非主键列进行查询

两步进行:
1)先根据非主键列设置一个key,存储的是key的值
2)然后根据查到的key再到第一步中的key中取查询具体的值.
即:
在关系型数据中,除主键外,还有可能其他列也步骤查询,
如上表中, username 也是极频繁查询的,往往这种列也是加了索引的.
转换到k-v数据中,则也要相应的生成一条按照该列为主的key-value
Set user:username:lurenjia:uid 1
这样,我们可以根据username:lurenjia:uid ,查出userid=1,
再查user:1:password/email …
完成了根据用户名来查询用户信息

Redis 使用中的常见问题

2.1 缓存穿透(缓存击穿)

2.1.1什么是缓存穿透?

一般的缓存系统,都是按照key去缓存查询,如果不存在对应的value,就应该去后端系统查找(比如DB)。如果key对应的value是一定不存在的,并且对该key并发请求量很大,就会对后端系统造成很大的压力。这就叫做缓存穿透。
缓存穿透简单说来就是缓存根本没用上了,缓存中不存在然后去DB查,然后DB查没有,然后不缓存,然后来了缓存中不存在又去DB查.

2.1.2 如何避免

1:对查询结果为空的情况也进行缓存,缓存时间设置短一点,或者该key对应的数据insert了之后清理缓存。
2: 使用互斥锁(mutex key)
业界比较常用的做法,是使用mutex。简单地来说,就是在缓存失效的时候(判断拿出来的值为空),不是立即去load db, 而是先使用缓存工具的某些带成功操作返回值的操作(比如Redis的SETNX或者Memcache的ADD)去set一个mutex key,当操作返回成功时,再进行load db的操作并回设缓存;否则,就重试整个get缓存的方法.
代码如下:

SETNX,是「SET if Not eXists」的缩写,也就是只有不存在的时候才设置,可以利用它来实现锁的效果。在redis2.6.1之前版本未实现setnx的过期时间,所以这里给出两种版本代码参考public String get(key) {String value = redis.get(key);if (value == null) { //代表缓存值过期//设置3min的超时,防止del操作失败的时候,下次缓存过期一直不能load dbif (redis.setnx(key_mutex, 1, 3 * 60) == 1) {  //代表设置成功value = db.get(key);redis.set(key, value, expire_secs);redis.del(key_mutex);} else {  //这个时候代表同时候的其他线程已经load db并回设到缓存了,这时候重试获取缓存值即可sleep(50);get(key);  //重试}} else {return value;      }}

8.2 缓存雪崩

8.2.1 什么是缓存雪崩?

当缓存服务器重启或者大量缓存集中在某一个时间段失效,这样在失效的时候,也会给后端系统(比如DB)带来很大压力。
即:
如果是数据从缓存中查询,如果没有则从mysql中查询,然后缓存到缓存中.这种模式在并发量并非太高或数据操作效率很高的情况下基本没有什么问题。
但是如果if(缓存失效 && 恰好遇到并发量很高 && 数据库操作时间长) then?
1. 缓存失效
2. 第一个进程去数据库获取新数据,假如包括SQL+程序逻辑耗时5S
3. 这5S内,第二个、第三个…第N个都只是获取到已失效的缓存,于是也都连接数据库…
4. 结果显而易见,数据库锁表 -> 数据库累计大量进程 -> 直至数据库挂掉!

8.2.2 如何避免?

1:在缓存失效后,通过加锁或者队列来控制读数据库写缓存的线程数量。比如对某个key只允许一个线程查询数据和写缓存,其他线程等待。
2:不同的key,设置不同的过期时间,让缓存失效的时间点尽量均匀。
3:做二级缓存,A1为原始缓存,A2为拷贝缓存,A1失效时,可以访问A2,A1缓存失效时间设置为短期,A2设置为长期.
4: 添加一个标记,类似文件锁,用于判断此时程序是否正在更新缓存。
若是,则直接返回旧缓存(标记有设置失效时间,避免由于程序错误导致标记未删除而引起的缓存不更新问题)
若否,则设置一个标记,然后进行数据获取及缓存更新,最后删除标记。

Redis 的key设计技巧缓存问题相关推荐

  1. redis热点key解决方案_缓存穿透,缓存雪崩,4种解决方案分析

    前言 设计一个缓存系统,不得不要考虑的问题就是:缓存穿透.缓存击穿与失效时的雪崩效应. 缓存穿透 缓存穿透是指查询一个一定不存在的数据,由于缓存是不命中时被动写的,并且出于容错考虑,如果从存储层查不到 ...

  2. redis key设计技巧

    1: 把表名转换为key前缀 如, user: 2: 第2段放置用于区分区key的字段--对应mysql中的主键的列名,如userid 3: 第3段放置主键值,如2,3,4...., a , b ,c ...

  3. 17 redis -key设计原则

    书签系统 create table book ( bookid int, title char(20) )engine myisam charset utf8;insert into book val ...

  4. Redis入门——3.Redis key的设计技巧

    Redis key的设计技巧 一,key设计原则 把表名转换为key前缀, 比如: tag: 第二段放置用于区分key的字段–对应mysql中的主键的列名 第三段放置主键值 第三段写列名 二,案例 用 ...

  5. 同程旅行王晓波:同程凤凰缓存系统在基于 Redis 方面的设计与实践(上篇)

    王晓波 同程旅行机票事业群 CTO 读完需要 12 分钟 速读仅需 4 分钟 本章和大家分享一下同程凤凰缓存系统在基于 Redis 方面的设计与实践.在本章中除了会列举我们工作过程中遇到各种问题和误区 ...

  6. Redis实战和核心原理详解(4)Redis存储Key的一种设计实现方式:模式匹配

    注意:此方案仅为演示Redis 的使用,正式生产环境切勿使用! 相关文章: Redis实战和核心原理详解(1)Centos7.0下安装Redis 5.0详细过程和使用常见问题 Redis实战和核心原理 ...

  7. 查看redis缓存大小_一个 bug 引发了服务器崩溃,对应 redis 的 key 回收原理你清楚了吗?...

    1 背景 项目中使用了 redis 做旁路缓存.读请求到来时,有以下操作:1.检查缓存,有则返回2.没有则读取数据库,将结果回写到缓存中. 写请求到来时,有以下操作:1.更新数据库 2.更新缓存(实际 ...

  8. 技术解读丨分布式缓存数据库Redis大KEY问题定位及优化建议

    摘要:如何定位分布式缓存数据库Redis大KEY问题,实操案例带你掌握优化方法. [背景] 访问Redis 5.0 cluster集群出现OOM报错,报错信息为(error) OOM command ...

  9. Redis基础,Linux下安装Redis和hredis,C++调用Redis,Redis中字符串设计

    文章目录 一.Redis是什么 Redis架构 Redis优势 Redis应用场景 二.Linux下载安装Redis(Ubuntu系统) 了解Redis版本 在线安装Redis 启动Redis服务端 ...

  10. Redis 布隆过滤器实战「缓存击穿、雪崩效应」

    Java高级互联网架构 2019-03-22 13:52:38 为什么引入 我们的业务中经常会遇到穿库的问题,通常可以通过缓存解决. 如果数据维度比较多,结果数据集合比较大时,缓存的效果就不明显了. ...

最新文章

  1. 史上最强iPhone越狱工具诞生,而且是开源!
  2. IO流介绍、java常用的几个IO流类之间的区别,以及各自的用法、使用场景
  3. 数理统计-5.4 三大抽样分布
  4. php文件夹重命名,php文件下载并重命名
  5. PHP文件系统-文件上传类
  6. PX4编译文件 Makefile 剖析
  7. (转)Spring4.2.5+Hibernate4.3.11+Struts1.3.8集成方案一
  8. Reverse digits of an integer
  9. 开源GIS(十五)——openlayers通过geoserver中WFS删除要素
  10. C++11 static_assert(转载)
  11. 【全网最全面C语言教程】C语言从入门到精通
  12. mmdetection学习之anchor_generator
  13. php里无法找到该网页,thinkphp搭建网站后端,入口文件找不到(无法加载)
  14. 电脑正常但windows安全中心有个黄色感叹号?
  15. 自制Anki选择题模板(支持桌面版/移动版)
  16. potoshope cs5 序列号
  17. 存进销系统 c语言大作业,c语言,程序设计大题,*纳税以系统(2)求法,求解...
  18. swper实现分页器样式修改
  19. python处理excel——创建excel工作簿和工作表并录入信息(openpyxl库)
  20. windows平台下的oracle ORA-01031的解决方法

热门文章

  1. sin(a-b)=sina*cosb-sinb*cosa的推导过程
  2. 学习3D建模电脑配置要求
  3. web中html+CSS修改背景图片的不透明度
  4. 淘宝API item_search_similar - 搜索相似的商品
  5. 什么是LTE CAT1和CATM
  6. JavaScript实现12进制的时钟特效
  7. Java中的标识符,关键字以及变量和常量
  8. 《Redis开发与运维》第一章 初识Redis 读书笔记
  9. 极智开发 | Go 安装教程
  10. CSS 实现 系统登录界面 (二)