redis 是一个开源的,内存中的数据结构存储系统,它可以用作数据库、缓存和消息中间件MQ。它支持多种类型的数据结构,如 字符串(strings),散列(hashes),列表(lists),集合(sets),有序集合(sorted sets)与范围查询,bitmaps,hyperloglogs和地理空间(geospatial)索引半径查询。redis内置了复制(replication),LUA脚本(lua scripting),LRU驱动事件(LRU eviction),事务(transcations),和不同级别的 磁盘持久化(persistence),并通过redis哨兵(sentinel)和自动分区(cluster)提供高可用性(high availbability)。

进入redis客户端

  1. # redis-cli
  2. 127.0.0.1:6379>

清除数据库

  1. 127.0.0.1:6379> flushdb
  2. OK
  3. 127.0.0.1:6379> keys *
  4. (empty list or set)

Redis-Key

  1. keys * //查看所有的key
  2. set name ray //set key
  3. get name //获取key
  4. EXISTS name //判断当前key是否存在
  5. move name 1 //移动到数据库 1
  6. del name //删除key
  7. 127.0.0.1:6379> expire name 10 //设置key的过期事件 单位是秒
  8. (integer) 1
  9. 127.0.0.1:6379> ttl name //查看当前key的剩余时间
  10. (integer) 7
  11. 127.0.0.1:6379> ttl name
  12. (integer) 3
  13. 127.0.0.1:6379> ttl name
  14. (integer) 1
  15. 127.0.0.1:6379> ttl name
  16. (integer) -2 // -2表示不存在
  17. 127.0.0.1:6379> type name //查看当前key的类型
  18. string

后面遇到不会的命令,可以去redis官网上查看http://redis.cn/commands.html

String(字符串)

  1. set key1 v1 // 设置值
  2. get key1 // 获得值
  3. keys * // 获取所有key
  4. exists key1 //判断key是否存在
  5. append key1 "hello" //追加字符串,如果没有key,就相当于set key
  6. strlen key1 // 获取自负床的长度
  7. ##########################################
  8. 127.0.0.1:6379> set views 0
  9. OK
  10. 127.0.0.1:6379> incr views //i++ 自增1
  11. (integer) 1
  12. 127.0.0.1:6379> get views
  13. "1"
  14. 127.0.0.1:6379> decr views //i-- 自减1
  15. (integer) 0
  16. 127.0.0.1:6379> get views
  17. "0"
  18. // 步长
  19. 127.0.0.1:6379> incrby views 10 //i+= 可以设置步长,指定增量
  20. (integer) 10
  21. 127.0.0.1:6379> get views
  22. "10"
  23. 127.0.0.1:6379> decrby views 5 //i-=
  24. (integer) 5
  25. 127.0.0.1:6379> get views
  26. "5"
  27. ##########################################
  28. // 字符串范围
  29. 127.0.0.1:6379> set key1 "hello,zhangsan"
  30. OK
  31. 127.0.0.1:6379> get key1
  32. "hello,zhangsan"
  33. 127.0.0.1:6379> getrange key1 0 3 //截取字符串 [0,3] 全闭!!不是半闭看开
  34. "hell"
  35. 127.0.0.1:6379> getrange key1 0 -1 //获取所有字符串 get key一样
  36. "hello,zhangsan"
  37. ##########################################
  38. // 字符串替换
  39. 127.0.0.1:6379> setrange key1 0 xx //替换指定位置开始的字符串
  40. (integer) 14
  41. 127.0.0.1:6379> get key1
  42. "xxllo,zhangsan"
  43. ##########################################
  44. // setex (set with expire) 设置过期时间
  45. // setnx (set if not exist) 不存在再设置(分布式锁中常常使用)
  46. 127.0.0.1:6379> setex name 10 ray // 设置10秒过期时间
  47. OK
  48. 127.0.0.1:6379> ttl name // 查看剩余时间
  49. (integer) 7
  50. 127.0.0.1:6379> ttl name
  51. (integer) -2 // -2表示已过期,key已经删除
  52. 127.0.0.1:6379> setnx name ray // 不存在name ,设置成功
  53. (integer) 1
  54. 127.0.0.1:6379> get name
  55. "ray"
  56. 127.0.0.1:6379> setnx name ray // 再次设置,存在name,设置不成功
  57. (integer) 0
  58. ##########################################
  59. // mset 批量插入
  60. // mget 批量获取
  61. 127.0.0.1:6379> mset key1 v1 key2 v2 key3 v3
  62. OK
  63. 127.0.0.1:6379> keys *
  64. 1) "key3"
  65. 2) "key1"
  66. 3) "key2"
  67. 127.0.0.1:6379> mget key1 key2 key3
  68. 1) "v1"
  69. 2) "v2"
  70. 3) "v3"
  71. ##########################################
  72. msetnx // 如果不存在,则批量插入
  73. 127.0.0.1:6379> msetnx key1 value1 key4 v4// 已经存在key1,插入失败 是哥原子性的操作,要么一起成功,要么一起失败
  74. (integer) 0
  75. 127.0.0.1:6379> keys *
  76. 1) "key3"
  77. 2) "key1"
  78. 3) "key2"
  79. ##########################################
  80. #对象
  81. 保存一个user1 {name:zhangsan,age:18},如何使用string去保存一个对象
  82. # 这里的key是一个巧妙的设计:user:{id}:{filed},如此设计redis是完全可以的
  83. 127.0.0.1:6379> mset user:1:name zhangsan user:1:age 18
  84. OK
  85. 127.0.0.1:6379> mget user:1:name user:1:age
  86. 1) "zhangsan"
  87. 2) "18"
  88. ##########################################
  89. getset getset
  90. 127.0.0.1:6379> getset db redis #如果不存在,则返回nil
  91. (nil)
  92. 127.0.0.1:6379> getset db mongodb # 如果存在值,获取原来的值。并设置新的值
  93. "redis"
  94. 127.0.0.1:6379> get db
  95. "mongodb"

String类型的使用场景:value除了是字符串还可以是数字

  • 计数器
  • 统计多单位的数量
  • 粉丝数
  • 对象缓存存储

List

在redis里面,我们可以把list完成 栈、队列、阻塞队列!
所有的list命令都是以l开头

  1. 127.0.0.1:6379> lpush list one # 将一个值或者多个值,插入到列表的头部
  2. (integer) 1
  3. 127.0.0.1:6379> lpush list two
  4. (integer) 2
  5. 127.0.0.1:6379> lpush list three
  6. (integer) 3
  7. 127.0.0.1:6379> LRANGE list
  8. (error) ERR wrong number of arguments for 'lrange' command
  9. 127.0.0.1:6379> LRANGE list 0 -1 # 获取list中所有值
  10. 1) "three"
  11. 2) "two"
  12. 3) "one"
  13. 127.0.0.1:6379> LRANGE list 0 0 # 通过区间获取具体的值
  14. 1) "three"
  15. ####################################################################################
  16. 127.0.0.1:6379> RPUSH list four #将一个值或者多个值,插入到列表尾部
  17. (integer) 4
  18. 127.0.0.1:6379> lrange list 0 -1
  19. 1) "three"
  20. 2) "two"
  21. 3) "one"
  22. 4) "four"
  23. 127.0.0.1:6379>
  24. ####################################################################################
  25. pop #弹出
  26. rpop
  27. lpop
  28. 127.0.0.1:6379> lrange list 0 -1
  29. 1) "three"
  30. 2) "two"
  31. 3) "one"
  32. 4) "four"
  33. 127.0.0.1:6379> lpop list #移除list的第一个元素
  34. "three"
  35. 127.0.0.1:6379> lrange list 0 -1
  36. 1) "two"
  37. 2) "one"
  38. 3) "four"
  39. 127.0.0.1:6379> rpop list #移除list的最后一个元素
  40. "four"
  41. 127.0.0.1:6379> lrange list 0 -1
  42. 1) "two"
  43. 2) "one"
  44. ####################################################################################
  45. lindex
  46. 127.0.0.1:6379> lindex list 0 # 通过下标获取list中的某个值
  47. "two"
  48. ####################################################################################
  49. llen #list长度
  50. 127.0.0.1:6379> LLEN list #返回列表的长度
  51. (integer) 2
  52. ####################################################################################
  53. 移除指定的值
  54. lrem
  55. 127.0.0.1:6379> lpush list three
  56. (integer) 3
  57. 127.0.0.1:6379> lpush list three
  58. (integer) 4
  59. 127.0.0.1:6379> lrange list 0 -1
  60. 1) "three"
  61. 2) "three"
  62. 3) "two"
  63. 4) "one"
  64. 127.0.0.1:6379> lrem list 1 one # 移除一个元素
  65. (integer) 1
  66. 127.0.0.1:6379> lrange list 0 -1
  67. 1) "three"
  68. 2) "three"
  69. 3) "two"
  70. 127.0.0.1:6379> lrem list 1 three
  71. (integer) 1
  72. 127.0.0.1:6379> lrange list 0 -1
  73. 1) "three"
  74. 2) "two"
  75. 127.0.0.1:6379> lpush list three
  76. (integer) 3
  77. 127.0.0.1:6379> lrem list 2 three #同时移除多个元素
  78. (integer) 2
  79. 127.0.0.1:6379> lrange list 0 -1
  80. 1) "two"
  81. 127.0.0.1:6379>
  82. ####################################################################################
  83. trim 修剪
  84. 127.0.0.1:6379> lpush mylist hello
  85. (integer) 1
  86. 127.0.0.1:6379> lpush mylist hello1
  87. (integer) 2
  88. 127.0.0.1:6379> lpush mylist hello2
  89. (integer) 3
  90. 127.0.0.1:6379> lpush mylist hello3
  91. (integer) 4
  92. 127.0.0.1:6379> lrange mylist 0 -1
  93. 1) "hello3"
  94. 2) "hello2"
  95. 3) "hello1"
  96. 4) "hello"
  97. 127.0.0.1:6379> ltrim mylist 1 2 # 移除1 2 之外的所有元素
  98. OK
  99. 127.0.0.1:6379> lrange mylist 0 -1
  100. 1) "hello2"
  101. 2) "hello1"
  102. 127.0.0.1:6379>
  103. ####################################################################################
  104. rpoplpush #移除列表的最后一个元素,并且添加到第一个元素
  105. 127.0.0.1:6379> lpush mylist one
  106. (integer) 1
  107. 127.0.0.1:6379> lpush mylist two
  108. (integer) 2
  109. 127.0.0.1:6379> lpush mylist three
  110. (integer) 3
  111. 127.0.0.1:6379> lrange mylist 0 -1
  112. 1) "three"
  113. 2) "two"
  114. 3) "one"
  115. 127.0.0.1:6379> RPOPLPUSH mylist myotherlist
  116. "one"
  117. 127.0.0.1:6379> lrange mylist 0 -1
  118. 1) "three"
  119. 2) "two"
  120. 127.0.0.1:6379> lrange myotherlist 0 -1
  121. 1) "one"
  122. 127.0.0.1:6379>
  123. 127.0.0.1:6379> lrange mylist 0 -1
  124. 1) "three"
  125. 2) "two"
  126. 3) "one"
  127. 4) "one"
  128. 127.0.0.1:6379> RPOPLPUSH mylist mylist
  129. "one"
  130. 127.0.0.1:6379> lrange mylist 0 -1
  131. 1) "one"
  132. 2) "three"
  133. 3) "two"
  134. 4) "one"
  135. 127.0.0.1:6379>
  136. ####################################################################################
  137. lset 更新指定下标的值
  138. 127.0.0.1:6379> exists list
  139. (integer) 0
  140. 127.0.0.1:6379> lset list 0 one #必须存在这个list,否则报错
  141. (error) ERR no such key
  142. 127.0.0.1:6379> lpush list one
  143. (integer) 1
  144. 127.0.0.1:6379> lset list 3 three # 下标不能超过范围
  145. (error) ERR index out of range
  146. 127.0.0.1:6379> lrange list 0 -1
  147. 1) "one"
  148. 127.0.0.1:6379> lset list 0 1 # 更新值
  149. OK
  150. 127.0.0.1:6379> lrange list 0 -1
  151. 1) "1"
  152. 127.0.0.1:6379>
  153. ####################################################################################
  154. linsert
  155. 127.0.0.1:6379> rpush list hello
  156. (integer) 1
  157. 127.0.0.1:6379> rpush list world
  158. (integer) 2
  159. 127.0.0.1:6379> lrange list 0 -1
  160. 1) "hello"
  161. 2) "world"
  162. 127.0.0.1:6379> LINSERT list before world go# 指定值前面插入一个值
  163. (integer) 3
  164. 127.0.0.1:6379> lrange list 0 -1
  165. 1) "hello"
  166. 2) "go"
  167. 3) "world"
  168. 127.0.0.1:6379> LINSERT list after hello redis#指定值后面插入一个值
  169. (integer) 4
  170. 127.0.0.1:6379> lrange list 0 -1
  171. 1) "hello"
  172. 2) "redis"
  173. 3) "go"
  174. 4) "world"

小结

  • 实际上list是一个链表,before node after,left,right 都可以插入值
  • 如果key不存在,创建新的链表
  • 如果key存在,新增内容
  • 如果移除了key,空链表,页代表不存在
  • 在两边插入或者改动值,效率最高!中间元素,效率会低一点

消息队列 (lpush rpop),栈(lpush lpop)

set

set中的值是不能重复的

  1. #############################################
  2. 127.0.0.1:6379> sadd myset hello #set 中添加元素
  3. (integer) 1
  4. 127.0.0.1:6379> sadd mysset ray
  5. (integer) 1
  6. 127.0.0.1:6379> SADD myset zhangsan
  7. (integer) 1
  8. 127.0.0.1:6379> SMEMBERS myset #查看指定set的所有值
  9. 1) "zhangsan"
  10. 2) "hello"
  11. 127.0.0.1:6379> SMEMBERS mysset
  12. 1) "ray"
  13. 127.0.0.1:6379> SISMEMBER myset hello #判断某个值是不是set集合中
  14. (integer) 1
  15. 127.0.0.1:6379> SISMEMBER myset world
  16. (integer) 0
  17. #############################################
  18. 127.0.0.1:6379> scard myset # 获取set集合中内容的个数
  19. (integer) 2
  20. #############################################
  21. 127.0.0.1:6379> scard myset
  22. (integer) 2
  23. 127.0.0.1:6379> SREM myset hello # 移除某个元素
  24. (integer) 1
  25. 127.0.0.1:6379> scard myset
  26. (integer) 1
  27. 127.0.0.1:6379> SMEMBERS myset
  28. 1) "zhangsan"
  29. #############################################
  30. set 无序不重复集合,随机抽取
  31. 127.0.0.1:6379> SMEMBERS myset
  32. 1) "zhangsan"
  33. 2) "ray"
  34. 3) "hello"
  35. 127.0.0.1:6379> SRANDMEMBER myset #随机获取一个元素
  36. "zhangsan"
  37. 127.0.0.1:6379> SRANDMEMBER myset
  38. "ray"
  39. 127.0.0.1:6379> SRANDMEMBER myset
  40. "ray"
  41. 127.0.0.1:6379> SRANDMEMBER myset 2 # 随机获取指定个数的元素
  42. 1) "zhangsan"
  43. 2) "ray"
  44. #############################################
  45. 删除指定的key,随机删除key
  46. 127.0.0.1:6379> SMEMBERS myset
  47. 1) "zhangsan"
  48. 2) "ray"
  49. 3) "hello"
  50. 127.0.0.1:6379> spop myset #随机删除一个元素
  51. "zhangsan"
  52. 127.0.0.1:6379> SMEMBERS myset
  53. 1) "ray"
  54. 2) "hello"
  55. 127.0.0.1:6379>
  56. #############################################
  57. 将指定的值,移动到另外一个set
  58. 127.0.0.1:6379> SMEMBERS myset
  59. 1) "zhangsan"
  60. 2) "ray"
  61. 3) "hello"
  62. 127.0.0.1:6379> spop myset
  63. "zhangsan"
  64. 127.0.0.1:6379> SMEMBERS myset
  65. 1) "ray"
  66. 2) "hello"
  67. 127.0.0.1:6379> sadd myset2 1
  68. (integer) 1
  69. 127.0.0.1:6379> sadd myset2 2
  70. (integer) 1
  71. 127.0.0.1:6379> SMEMBERS myset2
  72. 1) "1"
  73. 2) "2"
  74. 127.0.0.1:6379> SMOVE myset2 myset 1 #将指定的值,移动到另外一个set中
  75. (integer) 1
  76. 127.0.0.1:6379> SMEMBERS myset
  77. 1) "1"
  78. 2) "ray"
  79. 3) "hello"
  80. 127.0.0.1:6379> SMEMBERS myset2
  81. 1) "2"
  82. 127.0.0.1:6379>
  83. #############################################
  84. 微博,b站,共同关注(并集)
  85. 数字集合类:
  86. 差集
  87. - 交集
  88. - 并集
  89. 127.0.0.1:6379> sadd myset1 1
  90. (integer) 1
  91. 127.0.0.1:6379> sadd myset1 2
  92. (integer) 1
  93. 127.0.0.1:6379> sadd myset1 3
  94. (integer) 1
  95. 127.0.0.1:6379> sadd myset2 one
  96. (integer) 1
  97. 127.0.0.1:6379> sadd myset2 two
  98. (integer) 1
  99. 127.0.0.1:6379> sadd myset2 3
  100. (integer) 1
  101. 127.0.0.1:6379> SMEMBERS myset1
  102. 1) "1"
  103. 2) "2"
  104. 3) "3"
  105. 127.0.0.1:6379> SMEMBERS myset2
  106. 1) "3"
  107. 2) "two"
  108. 3) "one"
  109. 127.0.0.1:6379>
  110. 127.0.0.1:6379> SDIFF myset1 myset2 # 差集
  111. 1) "1"
  112. 2) "2"
  113. 127.0.0.1:6379> SDIFF myset2 myset1 # 差集
  114. 1) "one"
  115. 2) "two"
  116. 127.0.0.1:6379>
  117. 127.0.0.1:6379> SINTER myset1 myset2 #交集 共同好友
  118. 1) "3"
  119. 127.0.0.1:6379> SUNION myset1 myset2 # 并集
  120. 1) "two"
  121. 2) "3"
  122. 3) "1"
  123. 4) "2"
  124. 5) "one"
  125. 127.0.0.1:6379>

hash(哈希)

map集合,key-map集合,这时候这个值是一个map集合 本质和string类型没有太大区别,还是简单的k-v
set myhash field ray

  1. 127.0.0.1:6379> hset myhash name ray #set
  2. (integer) 1
  3. 127.0.0.1:6379> hget myhash name #get
  4. "ray"
  5. 127.0.0.1:6379> hmset myhash name zhangsan age 18 #批量set
  6. OK
  7. 127.0.0.1:6379> hmget myhash name age #批量get
  8. 1) "zhangsan"
  9. 2) "18"
  10. 127.0.0.1:6379>
  11. 127.0.0.1:6379> HGETALL myhash #获取hash的整体情况
  12. 1) "name"
  13. 2) "zhangsan"
  14. 3) "age"
  15. 4) "18"
  16. 127.0.0.1:6379>
  17. 127.0.0.1:6379> HDEL myhash age #删除field
  18. (integer) 1
  19. 127.0.0.1:6379> HGETALL myhash
  20. 1) "name"
  21. 2) "zhangsan"
  22. 127.0.0.1:6379>
  23. #############################################
  24. hlen
  25. 127.0.0.1:6379> hlen myhash
  26. (integer) 1
  27. #############################################
  28. hexists 判断hash中的key是否存在
  29. 127.0.0.1:6379> HEXISTS myhash address
  30. (integer) 0
  31. 127.0.0.1:6379> HEXISTS myhash name
  32. (integer) 1
  33. #############################################
  34. 只获取所有的field
  35. 只获取 所有的value
  36. 127.0.0.1:6379> hkeys myhash
  37. 1) "name"
  38. 2) "age"
  39. 127.0.0.1:6379> HVALS myhash
  40. 1) "zhangsan"
  41. 2) "18"
  42. 127.0.0.1:6379>
  43. #############################################
  44. incr decr
  45. 127.0.0.1:6379> HINCRBY myhash age 3
  46. (integer) 21
  47. 127.0.0.1:6379> HVALS myhash
  48. 1) "zhangsan"
  49. 2) "21"
  50. 127.0.0.1:6379> HINCRBY myhash age -1
  51. (integer) 20
  52. 127.0.0.1:6379> HVALS myhash
  53. 1) "zhangsan"
  54. 2) "20"
  55. #############################################
  56. hsetnx
  57. 127.0.0.1:6379> hsetnx myhash address "suzhou" 不存在才设置
  58. (integer) 1
  59. 127.0.0.1:6379> hsetnx myhash address "suzhou"
  60. (integer) 0

hash 变更的数据 user name age,尤其是用户信息之类的,经常变动的信息
hash更适合对象的存储,string更适合字符串存储

zset(有序集合)

在set基础上,增加了一个值,set k1 v1 ,zset k1 score1 v1

  1. 127.0.0.1:6379> zadd myzset 1 one #添加一个值
  2. (integer) 1
  3. 127.0.0.1:6379> zadd myzset 2 two
  4. (integer) 1
  5. 127.0.0.1:6379> zadd myzset 3 three 4 four #添加多个值
  6. (integer) 2
  7. 127.0.0.1:6379> ZRANGE myzset 0 -1
  8. 1) "one"
  9. 2) "two"
  10. 3) "three"
  11. 4) "four"
  12. #############################################
  13. 排序如何实现
  14. 127.0.0.1:6379> zadd salary 2500 xiaohong
  15. (integer) 1
  16. 127.0.0.1:6379> zadd salary 5000 zhangsan
  17. (integer) 1
  18. 127.0.0.1:6379> zadd salary 500 ray
  19. (integer) 1
  20. 127.0.0.1:6379> ZRANGEBYSCORE salary -inf +inf
  21. 1) "ray"
  22. 2) "xiaohong"
  23. 3) "zhangsan"
  24. 127.0.0.1:6379>
  25. 127.0.0.1:6379> ZRANGEBYSCORE salary -inf +inf withscores
  26. 1) "ray"
  27. 2) "500"
  28. 3) "xiaohong"
  29. 4) "2500"
  30. 5) "zhangsan"
  31. 6) "5000"
  32. 127.0.0.1:6379>
  33. #############################################
  34. 127.0.0.1:6379> ZREM salary xiaohong #移除
  35. (integer) 1
  36. 127.0.0.1:6379> zrange salary 0 -1
  37. 1) "ray"
  38. 2) "zhangsan"
  39. 127.0.0.1:6379>
  40. #############################################
  41. 127.0.0.1:6379> ZCARD salary # 获取集合的元素个数
  42. (integer) 2
  43. #############################################
  44. 127.0.0.1:6379> ZREVRANGEBYSCORE salary +inf -inf #倒叙
  45. 1) "zhangsan"
  46. 2) "ray"
  47. #############################################
  48. 获取区间的数量
  49. 127.0.0.1:6379> ZCOUNT salary 0 6000
  50. (integer) 2

set排序 存储班级成绩表,工资表排序
排行榜应用