[转帖]关于redis,你需要了解的几点!
一、关于 redis key:
1、是二进制安全的,也就是说,你可以使用任何形式的二进制序列来作为key,比如一个string,或者一个jpg图片的数据,需要说明的是,空字符串也是一个有效的key。
2、不建议使用过长的key,影响内存占用及数据查性能,对于过长的key,可以通过hash(例如SHA1)处理转换。
3、建议使用有意义及统一格式的key。
4、最大允许key大小为512M。
二、String 类型应用:
1、作为原子计数器:incr、decr、incrby
2、结合append命令,作为基于时间的增量序列。
3、随机访问及获取值区域,getrange、setrange。
附:需要注意的是append及range操作容易引起内存浪费和碎片化问题。
三、hash 类型:ziplist or hashtable
1、单个hash最多支持232 - 1个键值对。
2、关于hash类型的内部编码:ziplist(压缩列表) & hashtable(哈希表)
配置:hash-max-ziplist-entries(hash类型最大kv数据,默认512)、hash-max-ziplist-value(单个v值最大值, 默认64)
redis 采用何种结构取决于hash中元素数及元素值得大小,当同时满足小于配置时,redis使用ziplist编码存储,否则会转化为hashtable。
ziplist编码使用更加紧凑的结构实现多个元素的连续存储,因此占用的内存更小。
当数据类型无法满足配置条件,此时使用ziplist编码存储读写效率会下降,所以转换使用hashtable编码存储(O(1)时间复杂度)。
示例:添加 testuser hash类型key,先后设置元素name、desc不同长度元素值,分别查看内部编码类型
四、关于redis存储:redisObject
redis 对象内部存储形态。
1、type:数据类型、例如sting、hash、list、set、zset等,值类型查看命令【type】。
2、encoding:值存储内部实现的数据结构,具体可以参考第七部分。
3、lru:最后一次被访问时间,辅助回收,可以通过 object idletime {key} 在不更新lru属性情况下查看key的空闲时间。
4、refcount:当前对象被引用次数,辅助回收,可以通过 object refcount {key} 查看引用数,当对象为整数且值在范围在[0-9999]时,redis可以通过共享对象的方式来节省内存。
目前共享对象池只对整数设置了0~9999个共享对象,一方面整数对象池复用率最大,同时等值判断上时间复杂度为O(1)。
5、*ptr:数据存储或指向,数据本身或者指向数据的指针,redis3.0之后,长度在39以内的字符串数据,内部编码为embstr,内存创建时,字符串和redisObject一起分配,减少一次内存分配。
五、关于SDS
simple dynamic string:redis内部自定义简单动态字符串结构。
1、字符串属性的O(1)时间复杂度获取。
2、空间预分配、减少内存再分配。
3、惰性删除机制,字符串缩减后空间不释放,作为预分配空间保留。
六、关于对象属性存储:json or hash
对象属性存储可以通过整体json存储或者hash kv存储。具体应用选择,可以结合整体对象大小及属性操作需求来决定。
对于频繁整体操作,且对象数据量较小的一般采用json字符串类型存储。
对于多对象属性层级操作情景,可能hash会比较合适。
七、关于存储编码
如上图,同一种数据类型,可以有多种不同内部编码存储形式。具体redis采用那种编码形式与实际应用的数据值类型相关,如上述第三部分论述hash类型的编码转换。
数据的编码类型在数据写入的时候确定,不可变换,且只能向大内存编码行使转换。
如下,重新设置 testuser desc值,testuser对象的编码形式保持不变:
编码转换时机:
八、关于ziplist
通过第七节,我们可以看到hash、list、zset底层都有应用这种存储结构。
基本特点:
1、连续性内存存储。
2、可以模拟双向链表,O(1)时间复杂度内出入队操作。
3、读写性能跟数据的元素个数及值长度相关,适合存储小对象和长度有限的数据。
4、数据增删涉及复杂的内存操作。
ziplist基本结构:
1、zlbytes:int32类型、4字节,ziplist整体字节长度。
2、zltail:int32类型、4字节,记录距离尾节点偏移量,用于尾节点弹出。
3、zllen:int16类型,2字节,ziplist节点数量。
4、entry:数据节点,长度不定。
entry 即链表node,内部结构包含:
prev_entry_bytes_length:前一个节点所占用的空间,用户快速定位。
encoding:当前数据节点编码类型及长度,前两位标识编码类型,其余标识数据长度。
contents:节点数据值。
5、zlend:1字节,记录列表结尾。
九、关于redis内存消耗
redis内存消耗包括自身内存,键值对象占用、缓冲区内存占用及内存碎片占用。
1、缓冲区内存
包括客户端缓存、复制积压缓冲区及AOF缓冲区。
2、内存碎片
固定范围内存块儿分配。
redis默认使用jemalloc内存分配器,其它包括glibc、tcmalloc。
内存分配器会首先将可管理的内存分配为规定不同大小的内存块以备不同的数据存储需求,但是,我们知道实际应用中需要存储的数据大小不一,规范不一,内存分配器只能选择最接近数据需求大小的内存块儿进行分配,这样就伴随着“占不满”空间的碎片浪费。
jemalloc针对内存碎片有相应的优化策略,正常碎片率为mem_fragmentation_ratio在1.03左右。
第二部分我们说过,对string值得频繁append及range操作会会导致内存碎片问题,另外,第七部分,SDS惰性内存回收也会导致内存碎片,同时过期键内存回收也伴随着所释放空间的无法充分利用,导致内存碎片率上升的问题。
碎片处理:
应用层面:尽量避免差异化的键值使用,做好数据对齐。
redis服务层面:可以通过重启服务,进行碎片整理。
3、maxmemory 及 maxmemory-policy
redis 基于以上配置控制 redis 最大可用内存及内存回收。
需要注意的是内存回收执行影响redis的性能,避免频繁的内存回收开销。
[转帖]关于redis,你需要了解的几点!的更多相关文章
- 【转帖】 redis 命令 From https://www.cnblogs.com/zhouweidong/p/7550717.html
redis命令详解 redis中添加key value元素:set key value; 获取元素:get key ; redis中添加集合:lpush key value1 va ...
- 开始跟踪Redis啦,开帖
随着NoSql的流行,对这方面的产品开始关注起来,之前一直只是看看.从昨天开始决定把Redis的实现机制啃下来,毕竟代码量也就2W行. 每天花时间看看,记录下成果. here we go.
- Python celery和Redis入门安装使用(排难帖)
1.redis安装 下载地址 https://github.com/MicrosoftArchive/redis/releases,选择Redis-x64-3.2.100.msi5.8 MB下载就好了 ...
- [转帖]Redis持久化--Redis宕机或者出现意外删库导致数据丢失--解决方案
Redis持久化--Redis宕机或者出现意外删库导致数据丢失--解决方案 https://www.cnblogs.com/xlecho/p/11834011.html echo编辑整理,欢迎转载,转 ...
- [转帖]美团在Redis上踩过的一些坑-5.redis cluster遇到的一些问题
美团在Redis上踩过的一些坑-5.redis cluster遇到的一些问题 博客分类: redis 运维 redis clustercluster-node-timeoutfailover 转载请 ...
- [转帖]美团在Redis上踩过的一些坑-4.redis内存使用优化
美团在Redis上踩过的一些坑-4.redis内存使用优化 博客分类: 运维 redis redisstringhash优化segment-hash 转载请注明出处哈:http://carlosfu ...
- [转帖]美团在Redis上踩过的一些坑-3.redis内存占用飙升
美团在Redis上踩过的一些坑-3.redis内存占用飙升 博客分类: 运维 redis redismonitor内存突增client listinfo 转载请注明出处哈:http://car ...
- [转帖]美团在Redis上踩过的一些坑-2.bgrewriteaof问题
美团在Redis上踩过的一些坑-2.bgrewriteaof问题 博客分类: redis 运维 aofaof rewrite 转载请注明出处哈:http://carlosfu.iteye.com/b ...
- [转帖]美团在Redis上踩过的一些坑-1.客户端周期性出现connect timeout
美团在Redis上踩过的一些坑-1.客户端周期性出现connect timeout 博客分类: redis 运维 jedisconnect timeoutnosqltcp 转载请注明出处哈:http ...
- [转帖]TimesTen与Redis的对比
TimesTen与Redis的对比 2017-02-23 17:25:27 dingdingfish 阅读数 3682更多 分类专栏: TimesTen Oracle Redis In-Memory ...
随机推荐
- Spring Cloud Eureka 服务注册中心怎么配置
「Spring Cloud Eureka 入门系列」 Spring Cloud Eureka 入门 (一)服务注册中心详解 Spring Cloud Eureka 入门 (二)服务提供者详解 Spri ...
- 爬取Discuz!社区的教程标题
爬取Discuz!社区的教程标题-史上最详细解析(实现分页) 摘要:本文记录了爬取Discuz!社区的教程标题的详细过程,过程清晰 这是O的第一篇博客,如有排版问题请大佬见谅,O非常希望大佬能在评论区 ...
- 案例解析关于ArkUI框架中ForEach的潜在陷阱与性能优化
本文分享自华为云社区<深入解析ForEach的潜在陷阱与性能优化:错误用法与性能下降的案例分析>,作者:柠檬味拥抱 . 在ArkUI框架中,ForEach接口是基于数组类型数据进行循环渲染 ...
- 六步带你体验EDS交换数据全流程
本期我们将走进XX医疗集团向某慢病院共享数据的场景,如何通过EDS完成数据交换,进而实现医疗数据的安全可控共享. 本文分享自华为云社区<[EDS从小白到专家]第1期-六步带你体验EDS交换数据全 ...
- 数据湖探索DLI新功能:基于openLooKeng的交互式分析
摘要:基于华为开源openLooKeng引擎的交互式分析功能,将重磅发布便于用户构建轻量级流.批.交互式全场景数据湖. 在这个"信息爆炸"的时代,大数据已经成为这个时代的关键词之一 ...
- 解读分布式调度平台Airflow在华为云MRS中的实践
摘要:Airflow是一个使用Python语言编写的分布式调度平台,通过DAG(Directed acyclic graph 有向无环图)来管理任务. 本文分享自华为云社区<分布式调度平台Air ...
- vue-grid-layout数据可视化图表面板优化过程所遇问题汇总
对于drag事件不熟悉的,请先阅读:<drag事件详解:html5鼠标拖动排序及resize实现方案分析及实践> 之前老项目grafana面板,如下图所示(GEM添加图表是直接到图表编辑, ...
- Python 异步编程原理篇之新旧协程实现对比
协程的发展流程 再来回顾一下协程的发展流程: python2.5 为生成器引用.send()..throw()..close()方法 python3.3 为引入yield from,可以接收返回值,可 ...
- esp8266 水墨屏显示中文之全量字库
https://gitee.com/CHN_ZC/u8g2_wqy 项目中可以显示的中文字体有如下,以gb2312结尾的都是能够显示所有汉字的. 但是这些字体的容量都比较大,可能esp8266装不小, ...
- 服务降级,限流等--sentinel(SpringCloud Alibaba)
一. 介绍Sentinel,中文翻译为哨兵,是为微服务提供流量控制.熔断降级的功能,它和Hystrix提供的功能一样,可以有效的解决微服务调用产生的"雪崩"效应,为微服务系统提供了 ...