redis 数据类型详解 以及 redis适用场景场合( 三 )


Sorted Set
常用命令:zadd,zrange,zrem,zcard等使用场景:Redis sorted set的使用场景与set类似 , 区别是set不是自动有序的 , 而sorted set可以通过用户额外提供一个优先级(score)的参数来为成员排序 , 并且是插入有序的 , 即自动排序 。 当你需要一个有序的并且不重复的集合列表 , 那么可以选择sorted set数据结构 , 比如twitter 的public timeline可以以发表时间作为score来存储 , 这样获取时就是自动按时间排好序的 。 另外还可以用Sorted Sets来做带权重的队列 , 比如普通消息的score为1 , 重要消息的score为2 , 然后工作线程可以选择按score的倒序来获取工作任务 。 让重要的任务优先执行 。 实现方式:Redis sorted set的内部使用HashMap和跳跃表(SkipList)来保证数据的存储和有序 , HashMap里放的是成员到score的映射 , 而跳跃表里存放的是所有的成员 , 排序依据是HashMap里存的score,使用跳跃表的结构可以获得比较高的查找效率 , 并且在实现上比较简单 。
Pub/Sub
Pub/Sub 从字面上理解就是发布(Publish)与订阅(Subscribe) , 在Redis中 , 你可以设定对某一个key值进行消息发布及消息订阅 , 当一个key值上进行了消息发布后 , 所有订阅它的客户端都会收到相应的消息 。 这一功能最明显的用法就是用作实时消息系统 , 比如普通的即时聊天 , 群聊等功能 。
Transactions
谁说NoSQL都不支持事务 , 虽然Redis的Transactions提供的并不是严格的ACID的事务(比如一串用EXEC提交执行的命令 , 在执行中服务器宕机 , 那么会有一部分命令执行了 , 剩下的没执行) , 但是这个Transactions还是提供了基本的命令打包执行的功能(在服务器不出问题的情况下 , 可以保证一连串的命令是顺序在一起执行的 , 中间有会有其它客户端命令插进来执行) 。 Redis还提供了一个Watch功能 , 你可以对一个key进行Watch , 然后再执行Transactions , 在这过程中 , 如果这个Watched的值进行了修改 , 那么这个Transactions会发现并拒绝执行 。

  1. Redis实际应用场景
Redis在很多方面与其他数据库解决方案不同:它使用内存提供主存储支持 , 而仅使用硬盘做持久性的存储;它的数据模型非常独特 , 用的是单线程 。 另一个大区别在于 , 你可以在开发环境中使用Redis的功能 , 但却不需要转到Redis 。
转向Redis当然也是可取的 , 许多开发者从一开始就把Redis作为首选数据库;但设想如果你的开发环境已经搭建好 , 应用已经在上面运行了 , 那么更换数据库框架显然不那么容易 。 另外在一些需要大容量数据集的应用 , Redis也并不适合 , 因为它的数据集不会超过系统可用的内存 。 所以如果你有大数据应用 , 而且主要是读取访问模式 , 那么Redis并不是正确的选择 。 然而我喜欢Redis的一点就是你可以把它融入到你的系统中来 , 这就能够解决很多问题 , 比如那些你现有的数据库处理起来感到缓慢的任务 。 这些你就可以通过Redis来进行优化 , 或者为应用创建些新的功能 。 在本文中 , 我就想探讨一些怎样将Redis加入到现有的环境中 , 并利用它的原语命令等功能来解决 传统环境中碰到的一些常见问题 。 在这些例子中 , Redis都不是作为首选数据库 。 1、显示最新的项目列表下面这个语句常用来显示最新项目 , 随着数据多了 , 查询毫无疑问会越来越慢 。
SELECT * FROM foo WHERE ... ORDER BY time DESC LIMIT 10
在Web应用中 , “列出最新的回复”之类的查询非常普遍 , 这通常会带来可扩展性问题 。 这令人沮丧 , 因为项目本来就是按这个顺序被创建的 , 但要输出这个顺序却不得不进行排序操作 。类似的问题就可以用Redis来解决 。 比如说 , 我们的一个Web应用想要列出用户贴出的最新20条评论 。 在最新的评论边上我们有一个“显示全部”的链接 , 点击后就可以获得更多的评论 。我们假设数据库中的每条评论都有一个唯一的递增的ID字段 。我们可以使用分页来制作主页和评论页 , 使用Redis的模板 , 每次新评论发表时 , 我们会将它的ID添加到一个Redis列表:LPUSH latest.comments
我们将列表裁剪为指定长度 , 因此Redis只需要保存最新的5000条评论:LTRIM latest.comments 0 5000每次我们需要获取最新评论的项目范围时 , 我们调用一个函数来完成(使用伪代码):FUNCTION get_latest_comments(start, num_items):
id_list = redis.lrange("latest.comments",start,start+num_items - 1)IF id_list.length < num_itemsid_list = SQL_DB("SELECT ... ORDER BY time LIMIT ...")ENDRETURN id_list