首页 > 数据库 >Redis随笔

Redis随笔

时间:2023-04-09 22:55:29浏览次数:36  
标签:元素 Redis value 命令 key 集合 随笔

Redis

简介

Redis是一个开源的key-value存储系统。存储在内存中。

相比于Memcached,value类型相对更多,string、list、set、zset、hash。

Redis操作都是原子性的,单线程多路IO复用

Redis支持各种不同方式的排序。

 

keys * 查看当前库所有key

exists key 判断某个key是否存在

type key 查看你的key是什么类型

del key 删除指定的key

unlink key 根据value选择非阻塞删除

expire key 10 为key设定过期时间

ttl key 查看还有多少秒过期 -1永不过期、-2已过期

 

string

String 类型是二进制安全的。意味着 Redis 的 string 可以包含任何数据。比如 jpg 图片或者序列化的对象。

操作

set   <key><value>添加键值对 

*NX:当数据库中 key 不存在时,可以将 key-value 添加数据库
*XX:当数据库中 key 存在时,可以将 key-value 添加数据库,与 NX 参数互斥
*EX:key 的超时秒数
*PX:key 的超时毫秒数,与 EX 互斥

get <key>查询对应键值
append <key><value>将给定的<value> 追加到原值的末尾
strlen <key>获得值的长度
setnx <key><value>只有在 key 不存在时 设置 key 的值

incr <key>
将 key 中储存的数字值增 1
只能对数字值操作,如果为空,新增值为 1
decr <key>
将 key 中储存的数字值减 1
只能对数字值操作,如果为空,新增值为-1
incrby / decrby <key><步长>将 key 中储存的数字值增减。自定义步长。

mset <key1><value1><key2><value2> .....
同时设置一个或多个 key-value 对
mget <key1><key2><key3> .....
同时获取一个或多个 value
msetnx <key1><value1><key2><value2> .....
同时设置一个或多个 key-value 对,当且仅当所有给定 key 都不存在。

getrange <key><起始位置><结束位置>
获得值的范围,类似 java 中的 substring,前包,后包
setrange <key><起始位置><value>
用 <value> 覆写<key>所储存的字符串值,从<起始位置>开始(索引从 0 开始)。

setex <key><过期时间><value>
设置键值的同时,设置过期时间,单位秒。
getset <key><value>
以新换旧,设置了新值同时获得旧值。

数据结构

String 的数据结构为简单动态字符串(Simple Dynamic String,缩写 SDS)。是可以修改的字符串,内部结构实现上类似于 Java 的 ArrayList,采用预分配冗余空间的方式来减少内存的频繁分配.

List

单键多值
Redis 列表是简单的字符串列表,按照插入顺序排序。你可以添加一个元素到列表的头部(左边)或者尾部(右边)。

它的底层实际是个双向链表,对两端的操作性能很高,通过索引下标的操作中间的节点性能会较差。

操作

lpush/rpush <key><value1><value2><value3> .... 从左边/右边插入一个或多个值。
lpop/rpop <key>从左边/右边吐出一个值。值在键在,值光键亡。

rpoplpush <key1><key2>从<key1>列表右边吐出一个值,插到<key2>列表左边。

lrange <key><start><stop>  按照索引下标获得元素(从左到右)
lrange mylist 0 -1 0 左边第一个,-1 右边第一个,(0-1 表示获取所有)
lindex <key><index>按照索引下标获得元素(从左到右)
llen <key>获得列表长度

linsert <key> before <value><newvalue>在<value>的后面插入<newvalue>插入值
lrem <key><n><value>从左边删除 n 个 value(从左到右)
lset<key><index><value>将列表 key 下标为 index 的值替换成 value

数据结构

List 的数据结构为快速链表 quickList。

首先在列表元素较少的情况下会使用一块连续的内存存储,这个结构是 ziplist,也即是压缩列表。

它将所有的元素紧挨着一起存储,分配的是一块连续的内存。当数据量比较多的时候才会改成 quicklist。

因为普通的链表需要的附加指针空间太大,会比较浪费空间。比如这个列表里存的只是 int 类型的数据,结构上还需要两个额外的指针 prev 和 next。

Redis 将链表和 ziplist 结合起来组成了 quicklist。也就是将多个 ziplist 使用双向指针串起来使用。这样既满足了快速的插入删除性能,又不会出现太大的空间冗余。

 

Set

Redis set 对外提供的功能与 list 类似是一个列表的功能,特殊之处在于 set 是可以自动排重的,当你需要存储一个列表数据,又不希望出现重复数据时,set 是一个很好的选择,并且 set 提供了判断某个成员是否在一个 set 集合内的重要接口,

这个也是 list 所不能提供的。Redis 的 Set 是 string 类型的无序集合。它底层其实是一个 value 为 null 的 hash 表,所以添加,删除,查找的复杂度都是 O(1)。

一个算法,随着数据的增加,执行时间的长短,如果是 O(1),数据增加,查找数据的时间不变

操作

sadd <key><value1><value2> .....
将一个或多个 member 元素加入到集合 key 中,已经存在的 member 元素将被忽略
smembers <key>取出该集合的所有值。
sismember <key><value>判断集合<key>是否为含有该<value>值,有 1,没有 0
scard<key>返回该集合的元素个数。

srem <key><value1><value2> .... 删除集合中的某个元素。
spop <key>随机从该集合中吐出一个值。
srandmember <key><n>随机从该集合中取出 n 个值。不会从集合中删除 。
smove <source><destination>value 把集合中一个值从一个集合移动到另一个集合
sinter <key1><key2>返回两个集合的交集元素。
sunion <key1><key2>返回两个集合的并集元素。
sdiff <key1><key2>返回两个集合的差集元素(key1 中的,不包含 key2 中的)

数据结构

Set 数据结构是 dict 字典,字典是用哈希表实现的。Java 中 HashSet 的内部实现使用的是 HashMap,只不过所有的 value 都指向同一个对象。Redis 的 set 结构也是一样,它的内部也使用 hash 结构,所有的 value 都指向同一个内部值。

Hash

Redis hash 是一个键值对集合。
Redis hash 是一个 string 类型的 field 和 value 的映射表,hash 特别适合用于存储对象。
类似 Java 里面的 Map<String,Object>

用户 ID 为查找的 key,存储的 value 用户对象包含姓名,年龄,生日等信息,如果用普通的 key/value 结构来存储

操作

hset <key><field><value>给<key>集合中的 <field>键赋值<value>
hget <key1><field>从<key1>集合<field>取出 value
hmset <key1><field1><value1><field2><value2>... 批量设置 hash 的值
hexists<key1><field>查看哈希表 key 中,给定域 field 是否存在。
hkeys <key>列出该 hash 集合的所有 field
hvals <key>列出该 hash 集合的所有 value
hincrby <key><field><increment>为哈希表 key 中的域 field 的值加上增量 1 -1
hsetnx <key><field><value>将哈希表 key 中的域 field 的值设置为 value ,当且仅当域field 不存在 .

数据结构

Hash 类型对应的数据结构是两种:ziplist(压缩列表),hashtable(哈希表)。当field-value 长度较短且个数较少时,使用ziplist,否则使用hashtable。

Zset

Redis 有序集合 zset 与普通集合 set 非常相似,是一个没有重复元素的字符串集合。

不同之处是有序集合的每个成员都关联了一个评分(score),这个评分(score)被用来按照从最低分到最高分的方式排序集合中的成员。集合的成员是唯一的,但是评分可以是重复了 。

因为元素是有序的, 所以你也可以很快的根据评分(score)或者次序(position)来获取一个范围的元素。

访问有序集合的中间元素也是非常快的,因此你能够使用有序集合作为一个没有重复成员的智能列表。

操作

zadd <key><score1><value1><score2><value2>…     将一个或多个 member 元素及其 score 值加入到有序集 key 当中。

zrange <key><start><stop> [WITHSCORES]   返回有序集 key 中,下标在<start><stop>之间的元素

带 WITHSCORES,可以让分数一起和值返回到结果集。 zrangebyscore key minmax [withscores] [limit offset count]

返回有序集 key 中,所有 score 值介于 min 和 max 之间(包括等于 min 或 max )的成员。有序集成员按 score 值递增(从小到大)次序排列。

zrevrangebyscore key maxmin [withscores] [limit offset count]   同上,改为从大到小排列。

zincrby <key><increment><value> 为元素的 score 加上增量

zrem <key><value>删除该集合下,指定值的元素
zcount <key><min><max>统计该集合,分数区间内的元素个数
zrank <key><value>返回该值在集合中的排名,从 0 开始。

数据结构

SortedSet(zset)是 Redis 提供的一个非常特别的数据结构,一方面它等价于 Java的数据结构 Map<String, Double>,可以给每一个元素 value 赋予一个权重 score,另一方面它又类似于 TreeSet,内部的元素会按照权重 score 进行排序,可以得到每个元素的名次,还可以通过 score 的范围来获取元素的列表。

zset 底层使用了两个数据结构
(1)hash,hash 的作用就是关联元素 value 和权重 score,保障元素 value 的唯
一性,可以通过元素 value 找到相应的 score 值。

(2)跳跃表,跳跃表的目的在于给元素 value 排序,根据 score 的范围获取元素列表。

 

Bitmaps

(1) Bitmaps 本身不是一种数据类型, 实际上它就是字符串(key-value) ,但是它可以对字符串的位进行操作。

(2) Bitmaps 单独提供了一套命令, 所以在 Redis 中使用 Bitmaps 和使用字符串的方法不太相同。 可以把 Bitmaps 想象成一个以位为单位的数组,数组的每个单元只能存储 0 和 1, 数组的下标在 Bitmaps 中叫做偏移量。

 

 

 操作

setbit<key><offset><value>设置 Bitmaps 中某个偏移量的值(0 或 1)   偏移从0开始

getbit<key><offset>获取 Bitmaps 中某个偏移量的值   offset 位的值,从 0 开始算

  bitcount
统计字符串被设置为 1 的 bit 数。一般情况下,给定的整个字符串都会被进行计数,通过指定额外的 start 或 end 参数,可以让计数只在特定的位上进行。start 和 end 参数的设置,都可以使用负数值:比如 -1 表示最后一个位,而 -2 表示倒数第二个位,start、end 是指 bit 组的字节的下标数,二者皆包含。

举例: K1 【01000001 01000000  00000000 00100001】,对应【0,1,2,3】

bitcount<key>[start end] 统计字符串从 start 字节到 end 字节比特值为 1 的数量

  bitop 

bitop  and(or/not/xor) <destkey> [key…] 

bitop 是一个复合操作, 它可以做多个 Bitmaps 的 and(交集) 、 or(并集) 、 not(非) 、 xor(异或) 操作并将结果保存在 destkey 中。

 

 

 Redis 的发布和订阅 

1、 打开一个客户端订阅 channel1
    SUBSCRIBE channel1

2、打开另一个客户端,给 channel1 发布消息 hello

    publish channel1 hello

3、打开第一个客户端可以看到发送的消息

注:发布的消息没有持久化,如果在订阅的客户端收不到 hello,只能收到订阅后发布的消息

Redis 的事务

Redis 事务是一个单独的隔离操作:事务中的所有命令都会序列化、按顺序地执行。事
务在执行的过程中,不会被其他客户端发送来的命令请求所打断。
Redis 事务的主要作用就是串联多个命令防止别的命令插队

 

Multi  Exec  discard 

从输入 Multi 命令开始,输入的命令都会依次进入命令队列中,但不会执行,直到输入
Exec 后,Redis 会将之前的命令队列中的命令依次执行。
组队的过程中可以通过 discard 来放弃组队。

组队中某个命令出现了报告错误,执行时整个的所有队列都会被取消。 如果执行阶段某个命令报出了错误,则只有报错的命令不会被执行,而其他的命令都会执行,不会回滚。

WATCH key [key ...]

在执行 multi 之前,先执行 watch key1 [key2],可以监视一个(或多个) key ,如果在事务执行之前这个(或这些) key 被其他命令所改动,那么事务将被打断。

unwatch
取消 WATCH 命令对所有 key 的监视。
如果在执行 WATCH 命令之后,EXEC 命令或 DISCARD 命令先被执行了的话,那么就不需要再执行 UNWATCH 了。

 

Redis 事务三特性

单独的隔离操作
  事务中的所有命令都会序列化、按顺序地执行。事务在执行的过程中,不会被其他客户端发送来的命令请求所打断。

没有隔离级别的概念
  队列中的命令没有提交之前都不会实际被执行,因为事务提交前任何指令都
不会被实际执行

不保证原子性
  事务中如果有一条命令执行失败,其后的命令仍然会被执行,没有回滚

 

Redis持久化

Redis 提供两种持久化机制 RDB 和 AOF 机制:

1、 RDB(Redis DataBase)持久化方式:是指用数据集快照的方式半持久化模式 )记录 redis数据库的所有键值对 ,在某个时 间点将数据写入一 个临时文件,持久化结束 后,用这个临时文件替换上次持久化的文件,达到数据恢复 。

  优点:

  1、只 有一 个文 件 dump.rdb,方 便持 久化 。

  2、容 灾性 好,一个文件 可以 保存 到安 全的 磁盘 。

  3、性能最大化 ,fork 子进程来完成写操作, 让主进程继续 处理 命令 ,所 以是 IO最大化。使用 单独子进 程来进行持久化 ,主进程不会进 行任 何 IO 操作 。保证了 redis的高 性能 ) 4.相对于数据集大时 ,比 AOF的启动效 率更高。

  缺点:

  数据 安全 性低 。RDB 是间 隔一 段时 间进 行持 久化 ,如果 持久 化之 间 redis 发生故障 ,会 发生 数据 丢失 。所以这种方式更适合数据要求不严谨的时候 )

2、 AOFAppend-only file)持久化方式:是指所有的命令行记录以 redis 命令请求协议的格式完全持久化存储)保存为 aof 文件 。

  优点:

  1、数 据安 全, aof 持久 化可 以配 置 appendfsync 属性 ,有 always,每 进行 一次命令 操作 就记 录到 aof 文件 中一 次。

  2、通 过 append 模式 写文 件, 即使 中途 服务 器宕 机, 可以 通过 redis-check-aof工具 解决 数据 一致 性问 题。

  3、AOF 机制 的 rewrite 模式 。AOF文件没被 rewrite 之前( 文件过大时会对命令进行合并重写),可以删除其中的某些命令(比如 误操作的 flushall))

  缺点:

  1、 AOF文件比RDB文件大,且恢复速度慢 。
  2、数据集大的时候 ,比rdb启动效率低。

 

标签:元素,Redis,value,命令,key,集合,随笔
From: https://www.cnblogs.com/tyt0o0/p/17301364.html

相关文章

  • MongoDB、Redis、HBase、Cassandra、Elasticsearch、ClickHouse等NoSQL数据库简介及优
    MongoDBMongoDB是一个基于文档的NoSQL数据库,它使用BSON(二进制JSON)格式存储数据。MongoDB支持动态查询,可以轻松地处理非结构化数据。它还支持水平扩展,可以在多个节点上分布数据。优点:灵活性高,支持非结构化数据存储。支持水平扩展,可以在多个节点上分布数据。支持动态查询,可......
  • 解决Godot使用VsCode编写C#代码,智能提示不见了[一问随笔]
    问题:我的项目采用了godot+visualstudiocode+C#,有天突然换引擎,从Godot4.0.0升级到Godot4.0.2,visualstudiocode突然不给代码提示了,甚是奇怪。查看报错发现这样一句话找不到指定的sdk“godot.net.sdk/4.0.2”糟了!不会这个版本不支持用vscode写代码吧!解决方式:......
  • Linux安装Redis
    1.下载下载地址:https://redis.io/download  本人选择的是5.0.14版本  上传服务器。本人上传至usr/local目录下。2.解压  将解压后的redis-5.0.14文件夹改名为redis3.编译cd到/usr/local/redis目录,输入命令make执行编译命令,接下来控制台会输出各种编译过程中输......
  • 爬虫最后一天,爬取到的数据存到mysql中,爬虫和下载中间件、加代理、cookie、header、se
    爬到的数据存到mysql中classFirstscrapyMySqlPipeline:defopen_spider(self,spider):print('我开了')self.conn=pymysql.connect(user='root',password="",host='127.0.0.1......
  • 日常随笔2023.4.9
    #日常随笔2023.4.9​最近有些在脑海中有些许胡思乱想,我总是爱这样毫无边际的去幻想。这种行为是无法停止,所以倒不如尝试着回头去追忆自己想过的东西,一方面总结有用的经验,能加深自己的印象,另一方面,想和写是两码事情,想象可以没有逻辑,自由自在,但写作确实要讲究逻辑,不能任由散乱去......
  • 阿文随笔
    出差了两个月有余终于回来了,公司里的各种,都有点陌生了,原先几个比较熟悉的同事已经被派到其他的项目上去了,由于业务的原因大部分都不在上海了,短期内我又变得有些无助了。以前看过刘青云主演的《神探》,年轻的警察的内心写照是一个谨慎胆小的孩子,我的情况大概类似。下周又要出差了,姑......
  • Redis之父萨尔瓦多·桑菲利波又名安蒂雷斯
    萨尔瓦多·桑菲利波又名安蒂雷斯个人博客连接嗨,我是萨尔瓦多·桑菲利波,也被称为安提雷斯,一位居住在卡塔尼亚的意大利计算机程序员。我于7年1977月2020日出生在坎波贝洛迪利卡塔。2022年,我停止编写代码,开始全职写小说。现在,从<>年底开始,我再次编码,交替写作和编码。萨尔瓦......
  • java中操作redis
             ......
  • redis常用命令
               ......
  • mysql与redis如何保证数据一致性
    1.先更新MySQL数据库,再删除缓存,再从数据库查询到的最新的数据同步到redis。采用最终一致性性策略。缺点:相较于mq的方式,这种方式由于要查数据库并将最新数据写到redis,可能会造成接口响应速度变慢。2.更新mysql数据库,再采用mq异步的方式,将数据同步到redis中。缺点:数据同步延时......