Redis基础学习
Redis 官网:redis.io/
Redis 在线测试: http://try.redis.io/ 或 https://tool.chinaz.com/redis
Redis 命令参考:doc.redisfans.com/
redis下载:redisdesktop.com/download
redis-desktop-manager 的简单使用:www.cnblogs.com/godtrue/p/7…
一、Redis简述
- 关系型数据库(SQL):
- 适合处理一般量级数据,安全(如钱的存储)。
- 非关系型数据库(NOSQL):
- 为了处理海量数据,需要将关系型数据库的关系去掉。
- 适合处理海量数据,效率。不一定安全
关系型数据库(重要数据 ) + 非关系型数据库(海量操作数据不重要) = 项目
Redis是高性能键值对(key-value)数据库。目前支持的键值数据类型如下:
- 字符串类型
- 散列类型
- 列表类型
- 集合类型
- 有序集合类型
Redis的应用场景:
- 缓存(数据查询、短连接、新闻内容、商品内容等等)(最多使用)
- 聊天室的在线好友列表
- 任务列表(秒杀、抢购、12306等)
- 应用排行榜
- 网站访问统计
- 数据过期处理(可以精确到毫秒)
- 分布式集群架构中的session分离
二、测试基本命令
- ping 测试连接是否正常,如果正常会收到PONG
- set/get 设置数据、获取数据
- del 删除指定key的内容
- keys * 查看当前库中所有的key值
三、数据结构 🔥
redis是用键值对保存数据。key全部都是字符串,value有以下五种数据类型:
- 字符串(String)
- 哈希(hash)
- 字符串列表(list)
- 字符串集合(set)
- 有序字符串集合(sorted set)
Tips:key不要太长,也不要太短,最好有统一的命名规范
3.1、存储 String
字符串类型是Redis中最为基础、常用的数据存储类型,字符串在Redis中是二进制安全的,这便意味着该类型存入和获取的数据相同。在Redis中字符串类型的Value最多可以容纳的数据长度是512M。
常用命令:
- 赋值(相当于map.put):
set key value
:设定key持有指定的字符串value,如果该key存在则进行覆盖操作(如果赋予相同的key,新的value会覆盖老的value)。总是返回”OK“
- 取值(相当于map.get):
get key
:获取key的value。如果与该key关联的value不是String类型,redis将返回错误信息,因为get命令只能用于获取String value;如果该key不存在,返回 (nil)
-
删除(相当于map.remove):
del key
:删除指定key;返回值是数字类型,表示删了几条数据、 -
扩展命令:
getset key value
:先获取该key的值,然后在设置该key的值(重新赋值)。 返回的是之前的值
- 扩展命令:
append key value
:拼凑字符串。如果该key存在,则在原有的value后追加该值(返回的结果是字符串的长度);如果该key不存在,则重新创建一个key/value。
- 数值增(相当于++i):
incr key
:将指定的key的value原子性的递增1。如果该key不存在,其初始值为0,在incr之后其值为1。如果value的值不能转成整型,如hello,该操作将执行失败并返回相应的错误信息。
- 数值减(相当于--i):
decr key
:将指定的key的value原子性的递减1。如果该key不存在,其初始值为0,在incr之后其值为-1。如果value的值不能转成整型,如hello,该操作将执行失败并返回相应的错误信息。
注意:
- incr和decr 只能对字符串是数字的进行操作。
incrby key increment
:将指定的key的value原子性增加increment,如果该key不存在,其初始化值为0,在incrby之后,其值为increment。如果该值不能转成整型,如hello,则失败并返回错误信息decrby key decrement
:将指定的key的value原子性减少decrement,如果该key不存在,其初始化值为0,在decrby之后,其值为decrement。如果该值不能转成整型,如hello,则失败并返回错误信息
⏰ String使用环境: 主要用于保存json格式的字符串
3.2、存储 hash
Redis中的Hash类型可以看成 具有String Key和String Value的map容器。所以该类型非常适合于存储值对象的信息。如Username、Password和Age等。如果Hash中包含很少的字段,那么该类型的数据也将仅占用很少的磁盘空间。每一个Hash可以存储4294967295(231−12^{31} - 1231−1)个键值对。
Hash ---- {username:”张三”,age:”18”,sex:”man”} ---- javaBean
Hash特点:占用的磁盘空间极少
常用命令:
- 赋值
hset key field value
:为指定的key设定field/value对(键值对)hmset key field value [field2 value2 …]
:设置key中的多个filed/value
- 取值(单个值):
hget key filed
,返回指定的key中的field的值
- 取值(多个值):
hmget key fileds
,获取key中的多个filed的值

- 取值(所有值):
hgetall key
:获取key中的所有filed-vaule (字段名+字段值全部输出)

- 删除字段:
hdel key field [field...]
:可以删除一个或多个字段,返回值是被删除的字段个数

- 删除hash:
del key
,删除整个hash(注意这里是 del 不是 hdel)

- 增加数字:
hincrby key field increment
:设置key中field的值增加increment,如age增加20

- 扩展命令:
hexists key field
:判断指定的key中的field是否存在

- 扩展命令:
hlen key
:获取key 所包含的field的数量

- 扩展命令:
hkeys key
:获得所有的字段

- 扩展命令:
hvals key
:获得所有的value

- 扩展命令:
keys *
:查询所有的key

3.3、存储 list
List是按插入顺序排序的,头部(left)、尾部(right)。
- ArrayList使用数组方式存储,查询速度快,增加或删除速度慢
- LinkedList(重点)使用双向链表方式存储,插入或删除数据块,查询元素慢。Redis操作中,最多的是进行元素的增删,所以选取了链表。
双向链表中添加数据:

双向链表中删除数据:

list常用命令:
- 头部添加数据 :
lpush key values [values1 values2 ...]
,在指定的key所关联的list的头部插入所有的values,最后添加的在最前面。如果key不存在,插入之前会创建一个空链表,之后插入;插入成功,返回元素的个数

- 尾部添加数据 :
rpush key values [values1 values2 ...]
,在该list的尾部添加元素

- 查看列表:
lrange key start end
,获取链表中从start到end的元素的值。start、end:从0开始计数;也可以为负数,若为-1则表示链表尾部的元素,-2则表示倒数第二个,依次类推... (Tips:0 -1 是查询所有元素)

- 两端弹出(头部删除数据):
lpop key
- 返回并弹出指定的key关联的链表中的第一个元素,即头部元素
- 如果该key不存在,返回nil;如果key存在,返回链表的头部元素

- 两端弹出(头部删除数据):
rpop key
,删除并返回尾部元素

- 获取列表中元素的个数:
llen key
,返回链表个数, 返回指定的key关联的链表中的元素的数量

- 扩展命令(了解即可):
lpushx key value
:仅当参数中指定的key存在时,向关联的list的头部插入value,如果不存在,将不进行插入

- 扩展命令(了解即可):
rpushx key value
:在该list的尾部添加元素

- 扩展命令(了解即可):
lrem key count value
(效率极为低下,一般不建议使用): 删除count个值为value的元素,如果count大于0,从头向尾遍历并删除count个值为value的元素;如果count小于0,则从尾向头遍历并删除;如果count等于0,则删除链表中所有等于value的元素

- 扩展命令(了解即可):
lset key index value
(效率不高,通过索引替换元素,不建议使用): 设置链表中的index脚标的元素值为value,0代表链表的头元素,-1代表链表的尾元素。操作链表的脚标不存在则抛异常。注意,是替换设置,不是插入数据!

- 扩展命令(了���即可):
linsert key before|after pivot value
(效率不高): 在pivot 元素前面或者后面插入value这个元素

- 扩展命令(了解即可):
rpoplpush resource destination
: 将链表中的尾部元素弹出并添加到头部。[循环操作]:resource和destination都是自己。使用场景:如生产者和消费者的使用

3.4、存储 set
set是没有排序的字符集合,不允许出现重复的元素。作用:Redis操作中,涉及到两个大数据集合的并集、交集、差集运算,就使用set集合。
常用命令:
- 添加元素
sadd key values [value1 value2 ...]
:向set中添加数据,如果该key的值已有,则不会重复添加。数据添加进入后,是无序的

- 删除元素
srem key members [member1 member2 ...]
:删除set中指定的成员

- 获得集合中的所有元素
smembers key
: 获取set中所有的成员

- 获得集合中的单个元素
sismember key member
: 判断参数中指定的成员是否在该set中,1表示存在,0表示不存在或者该key本身就不存在(备注:无论集合中有多少元素都可以极速的返回结果)

- 集合的差集运算 A-B:
sdiff key1 key2 ...
:返回 key1 与 key2 中相差的成员,而且与key的顺序有关(A-B与B-A结果不同),即返回差集


- 集合的交集运算 A∩B :
sinter key1 key2 key3...
:返回交集


- 集合的并集运算 A∪B :
sunion key1 key2 key3...
:返回并集


- 扩展命令(了解):
scard key
,获取set中成员的数量

- 扩展命令(了解):
srandmember key
,随机返回set中的一个成员

-
扩展命令(了解):
sdiffstore destination key1 key2..
:将 key1 key2相差的成员存储在destination上 -
扩展命令(了解):
sinterstore destination key [key...]
:将返回的交集存储在destination上 -
扩展命令(了解):
sunionstore destination key [key...]
:将返回的并集存储在destination上
使用场景:
- set中可以放一些唯一性的数据,如IP地址
- 两个set中的同时有的,如同时购买两种商品的
3.5、存储 sortedset
了解即可,特点:有序、不重复
Sorted-set中每一个成员都会有一个分数(score)与之关联,通过分数来对成员进行从小到大的排序。且分数是可以重复的。使用场景:游戏排名、微博热点话题等。有序set集合,专门用来做排行榜
常用命令:
- 添加元素
zadd key score member [score2 member ...]
:将所有成员以及该成员的分数存放到Sorted-set中。如果该元素已存在则会用新的分数替换原有的分数;返回值是新加入到集合中的元素个数,不包含之前已经存在的元素。默认排序:分数由小到大

- 获得元素:
zscore key member
,返回指定成员的分数

- 获得元素:
zcard key
,获取集合中的成员数量

- 删除元素:
zrem key member [member...]
,移除集合中指定的成员,可以指定多个成员

- 范围查询:
zrange key start end [withscores]
:由小到大 获取集合中脚标为start到end的成员,[withscores] 参数表明返回的成员包含其分数

- 范围查询:
zrevrange key start stop [withscor es]
:由大到小 按照元素分数从大到小的顺序返回索引从start到stop的所有元素(包含两端的元素)

- 范围查询:
zremrangebyrank key start stop
:按照排名范围删���元素

- 范围查询:
zremrangebyscore key min max
:按照分数范围删除元素

- 扩展命令(了解):
zrangebyscore key min man [withscores] [limit offset count]
:返回分数在[min,max]的成员,并按照分数从低到高排序。[withscores]:显示分数;[limit offset count]:表明从脚标为offset的元素开始并返回count个成员

- 扩展命令(了解):
zincrby key increment member
:设置指定成员的增加的分数,返回值是更改后的分数

- 扩展命令(了解):
zcount key min max
:获取分数在[min,max]的成员

- 扩展命令(了解):
zrank key member
:返回成员在集合中的排名(从小到大)

- 扩展命令(了解):
zrevrank key member
:返回成员在集合中的排名(从大到小)

- 使用场景:
- 大型在线游戏的积分排行榜,积分发生变化,可通过zadd命令更新,然后通过zrange获取。
- sorted-set类型还可用于构建索引数据
四、keys的通用操作 🔥
Redis五种数据类型:string、list、set、hash和zset
通用命令如下:
keys pattern
:获取所有与pattern匹配的key,返回所有与该key匹配的keys。- *:表示任意0个或多个字符
- ?:表示任意一个字符
- keys *:表示查询所有key
- keys ????:表示查询长度是4位的key名
- keys *name*:表示查询key名中包含name的key

del key1 key2...
:删除指定的key

exists key
:判断该key是否存在,1代表存在,0代表不存在

rename key newkey
:为当前的key重命名

expire key
:设置过期时间,单位秒。如果某个key过��,redis会将其删除

ttl key
:获取该key所剩的超时时间。如果没有设置超时时间,返回-1。如果返回-2表示超时不存在。

type key
:获取指定key的类型。该命令将以字符串的格式返回。返回的字符串为 string、list、set、hash和zset。如果key不存在返回none

五、Java使用Redis
jedis: www.runoob.com/redis/redis…
jar包下载: mvnrepository.com/artifact/re…
import redis.clients.jedis.Jedis;
public class RedisStringJava {
public static void main(String[] args) {
//连接本地的 Redis 服务
Jedis jedis = new Jedis("localhost");
System.out.println("连接成功");
//设置 redis 字符串数据
jedis.set("runoobkey", "www.runoob.com");
// 获取存储的数据并输出
System.out.println("redis 存储的字符串为: "+ jedis.get("runoobkey"));
}
}
单实例连接:

连接池连接:

六、Redis特性
6.1、多数据库
一个Redis实例可以包含多个数据库,客户端可以指定连接某个redis实例的哪个数据库
一个Redis实例最多默认提供16个数据库,下标从0到15
数据操作默认都是在0号数据库上操作的,数据库相互之间不能共享键值对
select 0 连接0号数据库
select 1 连接1号数据库
move newkey 1 将当前库的key移植到1号库中

6.2、服务器命令
ping
:测试连接是否存活echo
:在命令行打印一些内容select
:选择数据库quit
:退出客户端连接dbsize
:返回当前数据库中key的数目info
:获取服务器的信息和统计flushdb
:删除当前选择数据库中的所有key (慎用)flushall
:删除所有数据库中的所有key (慎用)
6.3、消息订阅与发布
subscribe channel
:订阅频道,例:subscribe mychat,订阅mychat这个频道psubscribe channel*
:批量订阅频道,例:psubscribe s*,订阅以”s”开头的频道publish channel content
:在指定的频道中发布消息,如 publish mychat 'today is a newday'
步骤:

6.4、Redis事务
6.4.1、事务概念
Redis作为NoSQL数据库也提供了事务机制。在Redis中,MULTI
、EXEC
、DISCARD
这三个命令是我们实现事务的基石。
- MySQL-事务:目的为了保证数据完整性,安全。
- Redis-事务:目的为了进行redis语句的批量化执行
6.4.2、redis事务特征
- 事务中所有命令都将被串行化的顺序执行,事务执行期间,redis不会再为其他客户端的请求提供任何服务,从而保证事务中所有命令被原子的执行;
- 和关系型数据库的事务相比,在redis事务中如果有某一条命令执行失败,其他的命令仍然会被继续执行;
- 通过
MULTI
开启一个事务,同等为“begin transaction”语句。在该语句之后执行的命令被视为事务之内的操作,最后可以通过执行EXEC/DISCARD
命令来提交/回滚事务内的所有操作,等同于“commit/rollback”语句; - 在事务开启之前,如客户端与服务器网络断开,气候所待执行的语句都不会被服务器执行。如果中断发生在执行EXEC命令之后,那么该事务中所有命令都会被服务器执行;
6.4.3、命令解释
multi
:开启事务用于标记事务的开始,其后执行的命令都将被存入命令队列,直到执行EXEC时,这些命令才会被原子的执行,类似与关系型数据库中的:begin transactionexec
:提交事务,类似与关系型数据库中的:commit 执行批量化discard
:事务回滚,类似与关系型数据库中的:rollback 不执行批量化操作
6.4.4、测试事务
正常执行事务:

回滚:

失败命令:

6.5、Redis持久化
6.5.1、概述
Redis的数据是存储在内存中的。为了重启后数据不丢失,需要将数据从内存中同步到硬盘中,这个过程就是持久化。
两种方式持久化:一种是RDB方式,一种是AOF方式
- RDB持久化(默认支持,无需配置)
- 该机制是指在指定的时间间隔内将内存中的数据集快照写入磁盘
- AOF持久化
- 改机制将以日志形式记录服务器所处理的每一个写操作,Redis服务器启动时会读取该文件来重新构建数据库
- 无持久化
- 配置方式可以禁用Redis服务器持久化功能
- redis可以同时使用RDB和AOF
6.5.2、RDB
RDB相当于照快照。保存的是一种状态。
优点:①快照保存数据速度极快,还原数据速度极快
②适用于灾难备份
缺点:①小内存机器不适合使用。
适用于:内存比较充裕的计算机。
6.5.3、AOF
使用日志功能保存数据操作。默认AOF机制关闭的。
AOF操作:只会保存导致key变化的语句
优点:①持续性占用极少量的内存资源
缺点:①日志文件会特别大,不适用于灾难恢复
②恢复效率远远低于RDB
适用于:内存比较小的计算机
七、Redis使用场景
转载自:https://juejin.cn/post/7395946284320768034