Redis基础
基础知识
- Redis有16个数据库,默认使用第0个数据库
select
+number
: 选择使用的数据库
DBSIZE
:查看数据库大小
keys *
:查看数据库所有的key
flushdb
:清空当前数据库
flushall
:清空全部数据库 - Redis是单线程的
官方表示,Redis是基于内存操作,CPU不是Redis性能瓶颈,Redis的瓶颈是根据机器的内存和网络带宽。所以使用单线程也是完全可以的。Redis是使用C语言编写,官方的数据为100000+的QPS,这完全不比同样是使用可以key-value的Memecache差。
关于RedisKey的基本命令
Redis是一个开源(BSD许可)的,内存中的数据结构存储系统,它可以用作数据库缓存和消息中间件。它支持多种类型的数据结构,如 字符串(Strings), 散列(hashes), 列表(lists), 集合(sets),有序集合(sorted sets)与范围查询,bitmaps,hyperloglogs 和 地理空间(geospatial)索引半径查询。Redis内置了 复制(replication),LUA脚本(Lua scripting),LRU驱动事件(LRU eviction),事务(transaction)和 不同级别的磁盘持久化(persistence),并通过Redis哨兵(Sentinel)和自动分区(Cluster)提供高可用性(high availability)。
select
+ number
: 选择使用的数据库
DBSIZE
:查看数据库大小
keys *
:查看数据库所有的key
flushdb
:清空当前数据库
flushall
:清空全部数据库
EXISTS
+字段名
:查询字段是否存在
move
+字段名
:移除字段名
set
+字段名
+字段值
:设置字段名字段值
get
+字段名
:获取该字段名的字段值
EXPIRE
+字段名
+seconds
:设置字段名过期时间
ttl
+字段名
:查看字段生效剩余时间
type
+字段名
:查看字段名类型
APPEND
+字段名
+字段值
:往一个字段名里加一个字段值,如果字段名不存在,相当于set
STRLEN
+字段名
:查看字段长度
incr
+integer类型字段名
:integer类型字段数值+1
incrby
+integer类型字段名
+数值
:一次增加指定数值
decr
+integer类型字段名
:integer类型字段数值-1
decrby
+integer类型字段名
+数值
:一次减少指定数值
五大数据类型
1. String(字符串)
SET key value
含义:
将字符串值 value 关联到 key 。
如果 key 已经持有其他值, SET 就覆写旧值,无视类型GETRANGE
+字段名
+起始值索引
+终止索引值
获取一个String类型中部分字符
getrange view 0 -1
: 查看view的全部字符串 ,相当于get view
SETRANGE
+字段名
+起始位置索引
+需要替换的值
替换指定位置开始的字符串
SETEX key seconds value
含义:
将值 value 关联到 key ,并将 key 的生存时间设为 seconds (以秒为单位)。
如果 key 已经存在, SETEX 命令将覆写旧值。
返回值:
设置成功时返回 OK 。
当 seconds 参数不合法时,返回一个错误。SETNX key value
含义:
将 key 的值设为 value ,当且仅当 key 不存在。
若给定的 key 已经存在,则 SETNX 不做任何动作。
SETNX 是【Set if Not Exists】(如果不存在,则 SET)的简写。
返回值:
设置成功,返回 1 。
设置失败,返回 0 。GETSET key value
含义:
将给定 key 的值设为 value ,并返回 key 的旧值(old value)。
当 key 存在但不是字符串类型时,返回一个错误。
返回值:
返回给定 key 的旧值。
当 key 没有旧值时,也即是, key 不存在时,返回 null 。mset/mget
同时设置/获取多个键值
语法:MSET key value [key value …]
MGET key [key …]
- 博客的字数统计如何实现?(strlen)
- 如何将审计日志不断追加到指定key?(append)
- 你如何实现一个分布式自增id?(incr-雪花算法)
- 如何实现一个博客的的点赞操作?(incr,decr)
2. List列表
在redis里,list可以是栈,是队列,是阻塞队列
所有的list命令都是以L开头
在实际上,List列表是一个链表 before after right left 都可以进行插入
如果key则创建新的列表,如果key存在则执行命令
对列表两边元素进行操作效率最高,中间元素相对来说效率更低
#Lpush + 列表名 + 字段值[...]:将一个或多个值插入到列表头部(左)
127.0.0.1:6379> Lpush list one
(integer) 1
127.0.0.1:6379> Lpush list two
(integer) 2
127.0.0.1:6379> Lpush list three
(integer) 3
#Lrange + 列表名 + 起始位置 + 结束位置:查询列表中起始位置到结束位置的值,0 -1表示所有
127.0.0.1:6379> Lrange list 0 -1
1) "three"
2) "two"
3) "one"
127.0.0.1:6379> Lrange list 0 1
1) "three"
2) "two"
#Rpush + 列表名 + 字段值[...]:将一个或多个值插入到列尾部(右)
127.0.0.1:6379> Rpush list zero
(integer) 4
127.0.0.1:6379> Lrange list 0 -1
1) "three"
2) "two"
3) "one"
4) "zero"
#Lpop + 列表名 + 需要删除个数n:从列表头部(左)删除n个值
127.0.0.1:6379> Lpop list 2
1) "three"
2) "two"
127.0.0.1:6379> lrange list 0 -1
1) "one"
2) "zero"
#Rpop + 列表名 + 需要删除个数n:从列表尾部(右)删除n个值,如果不写n则默认为1
127.0.0.1:6379> Rpop list
"zero"
127.0.0.1:6379> lrange list 0 -1
1) "one"
127.0.0.1:6379> lrange list 0 -1
1) "5"
2) "4"
3) "3"
4) "2"
5) "1"
6) "0"
#Lindex + 列表名 + 索引值;查询索引值的字段值
127.0.0.1:6379> lindex list 0
"5"
#Llen + 列表名:返回列表的长度
127.0.0.1:6379> llen list
(integer) 6
127.0.0.1:6379> lrange list 0 -1
1) "5"
2) "5"
3) "4"
4) "3"
5) "2"
6) "0"
#Lrem + 表名 + 需要删除的个数 + 需要删除的值
127.0.0.1:6379> lrem list 2 5
(integer) 2
127.0.0.1:6379> lrange list 0 -1
1) "4"
2) "3"
3) "2"
4) "0"
#Ltrim + 列表名 + 起始位置 + 终止位置:将列表截取为从起始位置到终止位置
127.0.0.1:6379> ltrim list 1 2
OK
127.0.0.1:6379> lrange list 0 -1
1) "3"
2) "2"
#rpoplpush + 原列表名 + 新列表名:将原列表最后一个元素移除,并且移动到新的列表
127.0.0.1:6379> rpoplpush list list2
"2"
127.0.0.1:6379> lrange list 0 -1
1) "3"
127.0.0.1:6379> lrange list2 0 -1
1) "2"
#Lset 列表名 索引值 替换的值:将该索引绑定的字段值替换成新值,如该值不存在,则提示ERR no such key
127.0.0.1:6379> lset list 0 wang
(error) ERR no such key
127.0.0.1:6379> lpush list qiang xiang lang
(integer) 3
127.0.0.1:6379> lset list 0 wang
OK
127.0.0.1:6379> lrange list 0 -1
1) "wang"
2) "xiang"
3) "qiang"
#Linsert 列表名 before|after 字段值i 新插入的字段值n:在列表的字段i前/后插入新的字段值n
127.0.0.1:6379> linsert list after wang qing
(integer) 4
127.0.0.1:6379> lrange list 0 -1
1) "wang"
2) "qing"
3) "xiang"
4) "qiang"
- 如何基于redis实现一个队列结构?(lpush/rpop)
- 如何基于redis实现一个栈结构?(lpush/lpop)
- 如何基于redis实现一个阻塞式队列?(lpush/brpop)
- 如何实现秒杀活动的公平性?(先进先出-FIFO)
- 通过list结构实现一个消息队列(顺序)吗?(可以,FIFO->lpush,rpop)
- 用户注册时的邮件发送功能如何提高其效率?(邮件发送是要调用三方服务,底层 通过队列优化其效率,队列一般是list结构)
- 如何动态更新商品的销量列表?(卖的好的排名靠前一些,linsert)
- 商家的粉丝列表使用什么结构实现呢?(list结构)