从门外到门内: redis

作者: Ljian1992 | 来源:发表于2017-04-16 19:10 被阅读328次

相关资料:

  1. 官网
  2. 文档
  3. 好书: redis实战(书中的代码), Redis开发运维实践指南
  4. 好文: 关于Redis的常识

Redis数据类型的使用

具体那五种数据类型有什么特点,请看关于Redis的常识里面总结得非常好。需要补充一下的是对于列表,散列,有序集合,当长度和里面的值得大小在一定范围时,redis会选择使用ziplist结构来存储。对于集合会使用zset来存储,节省内存。长度和大小都可以通过配置文件来指定,默认是少于512个且最长那个值不超过64字节时使用。由于涉及到编码解码问题,设置太大会有性能问题。重点,可以通过conn.debug_object(key)来查看,相关信息。

在redis的各种数据结构中,要注意O(n)的操作,尽量规避,由于redis是单线程模型,进行一个耗时操作时,会影响其它客户端的操作。

使用哪种数据结构需要根据使用场景来决定,主要的思路(确定后看看文档相关操作的时间复杂度):

  1. 是否有序
  2. 是否需要不重复
  3. 侧重点是增删改查的哪一种或多种
  4. 内存占用, 注意,集合的个数*集合里面的元素个数,不同的搭配会有不同的效果, 即便
  5. 性能要求
  6. 是否存在O(n)类型的操作

redis的最佳实践

del 操作性能问题:

del set, sorted set , hash 的时间复杂度是O(m),m是集合里面的数据, 因此对于数据量较大的结合,不要直接一次性删除。应当采用:重命名 + 批量删除逐渐删除

用scan代替keys命令, 因为keys会遍历整个数据

查看redis的状况的命令:

  1. info commandstats: 查看命令的运行情况, 可以看出哪些命令运行的慢

  2. config resetstat:重置commandstats

  3. redis-cli -h localhost -p 6379 client list | grep -v "omem=0": 快速排查redis慢的神奇命令,阻塞是omem升高

  4. slowlog get|len | reset

尽可能使用不超过1M大小的KV

因为这样会导致redis的内存碎片增加,导致rss占用较大

尽可能使用pipeline操作&批量操作命名,减少网络传输的开销

对于set, sorted set,使用pipeline时可以将集合操作的结果存入一个预先定义的key中,这样就可以

减少对大数据集合的高时间复杂度的操作

性能提升思路,减少操作中集合元素的数量。

  1. 将宽集合转为高集合(类似于mysql中的水平切分)
  2. 遇到set 和 sorted set 有很多交集和并集执行,调整多个交集并集的顺序,较少redis的处理量。(一般来说,先进行交集操作再进行并集操作)

降低内存的方式

列表,散列,有序集合,当长度和里面的值得大小在一定范围时,redis会选择使用ziplist结构来存储。对于集合会使用zset来存储,节省内存。利用短结构结合分片,来降低内存的使用。由于长度的限制,需要利用分片技术来将扩展存储空间。instagram节约内存的著名例子

redis内存过期策略

过期策略

  1. 定时删除(基本没人用)
    含义:在设置key的过期时间的同时,为该key创建一个定时器,让定时器在key的过期时间来临时,对key进行删除
    缺点:若key过多,删除key太耗cpu, 定时器创建耗时
    优点:保证内存尽快释放

  2. 惰性删除
    含义:key过期的时候不删除,每次从数据库获取key的时候去检查是否过期,若过期,则删除
    缺点:若大量的key在超出超时时间后,很久一段时间内,都没有被获取过,那么可能发生内存泄露
    优点:删除操作只发生在从数据库取出key的时候发生,而且只删除当前key,所以对CPU时间的占用是比较少的

  3. 定期删除
    含义:每隔一段时间执行一次删除过期key操作
    特点:CPU时间友好和内存友好方面介于定时删除和惰性删除直接,折中。
    难点:定期删除的频率?删除执行的时长

redis采用的方式: 惰性删除+定期删除

redis的常见应用场景

  1. 取最新的N个数据操作

    例如取文章最新的100条评论的ID放到list集合中

  2. 以某些条件未权重的排行榜应用,取TOP N操作

    利用sorted set 结构,排序条件设置为score, 具体数据设置成value

  3. 各种计数

    例如,电商的商品的各种计数(喜欢,评论,点赞),利用hash结构存储不同维度的计数

  4. 存储社交关系

    将用户的好友,存在sorted set 中,value为用户id, score为时间戳,求两个人的好友,交集即可。好友巨多应该就不能这样用

  5. 构建队列系统

    List可以很方便的利用相关命令来构建队列

  6. 缓存

    redis提供丰富的数据类型,本身就可以当分布式缓存使用。很多框架本身提供相应的功能,通过配置就可以让redis作为缓存层,例如将redis配置为django的缓存层。

  7. 实现boomfilter

    redis中的string类型提供位操作,所以可以利用redis实现一个分布式的boomfilter。 这里有别人实现的

  8. 分布式锁

    主要思路是利用setnx,和BLPOP或者是BRPOP命令来实现。例如阻塞锁的实现思路,clientA通过setnx设置锁,ClientB再设置的时候,已经存在了,此时则通过BLPOP阻塞,当ClientA通过del 命令删除锁并LPUSH到相对于的队列中,此时ClientB就结束阻塞了。 具体,可以参考某大大的实现

  9. 搜索引擎

例如文档内容搜索,利用set构建反向索引,并集搜索同义词,交集搜索多个次,差集做搜索排除。利用sort命令对搜索结果进行排序,利用sorted set 的交集对搜索结果进行多维度排序。具体,可以看redis 实战的第七章

一些与redis相关的github热门项目

retools
scrapy-redis
redis-tools
python-redis-lock
pyreBloom

相关文章

  • 从门外到门内: redis

    相关资料: 官网 文档 好书: redis实战(书中的代码), Redis开发运维实践指南 好文: 关于Redis...

  • 门内•门外

    我紧握着这把发锈的门把,推开了这扇沉重的大门;门外面,有什么? “疯子。” 我被迫在精神病院里待了六年,与...

  • 门内·门外

    6:30am的闹钟响了! 对着镜子整理自己的那10分钟我习惯不急不慢。 吃下一碗老妈定时煮好的粥, 进房看一眼那对...

  • 门内,门外

    夜来了, 关上门。 门外是他们的世界, 像3d立体音效的大电影。 门内是我的世界, 像无声的黑白影片。

  • 从门外到门内:Linux基础知识

    最近在兼职部分运维工作,之前没怎么做过,对Linux不是那么的熟悉,这导致的主要问题是,当出现性能问题,不知道看那...

  • 现代诗·门

    门内门外 两个世界 门外流浪 门内安睡 门内是长江 门外是大海 那是海门 门内是家 门外是它 那是宅门 有看得见的...

  • 门内与门外

    门内与门外的智慧虽只隔着一扇门,却是差了不止万里! 学习《门内智慧“谋局者”》 真正让我认识到什么是—— 门外假传...

  • 门内门外

    只有一条路 却有那么多门 门外的是走廊 门内的是幻想 走廊的尽头挂着一扇窗 幻想的喘息吐出两条火光 窗子拥着一个女...

  • 门内门外

    住所的房屋隔音做得不好,总会传来隔壁邻居的各种动静。 楼下的邻居每天早出晚归。第一次听见动静是一天夜半时分有人大声...

  • 门内门外

    一道门兀立 隔开两个世界 一边是X 一边是Y 一边是白天 一边是黑夜 一边是脚步 一边是耳朵 脚步踩着光线行走 耳...

网友评论

    本文标题:从门外到门内: redis

    本文链接:https://www.haomeiwen.com/subject/bloaattx.html