Redis的数据类型
关系型数据库和非关系型数据库结构的区别
1.关系型数据库
常见的关系型数据库:Oracle、DB2、SQL Server、MySQL等
关系型数据库最典型的数据结构就是表,由二维表及其之间的联系所组成
2.非关系型数据库
常见的非关系型数据库:MongoDB、Redis等
非关系型数据库严格来讲不算是一种数据库,应该是一种数据结构化存储方法的集合,可以是文档或者键值对等
NoSQL是什么,出现的目的和意义是什么
NoSQL泛指的是非关系型数据库,它可以作为良好的关系型数据库的补充
NoSQL数据库的产生是为了解决大规模数据集合多重数据种类带来的挑战,尤其是大数据应用难题
redis数据类型介绍
redis是一个key-value存储系统。和Memcached类似,它支持存储的value类型相对更多,包括string(字符串)、list(链表)、set(集合)、zset(sorted set --有序集合)和hash(哈希类型)。这些数据类型都支持push/pop、add/remove及取交集并集和差集及更丰富的操作,而且这些操作都是原子性的,因为redis的执行方式是单线程+多路IO复用。
介绍的内容
Redis五大基本类型
- String
- List
- Set
- Zset
- Hash
这些类型只表示值的类型,键的类型是固定不变的String
String(字符串)
- String是最基本的类型, 一个key对应一个value
- String类型是二进制安全的,意味着Redis的String可以包含任何数据,比如jpg图片或者序列化对象
- redis中字符串value最多可以是512M,字符串的最大长度512M
常用命令
赋值语句 set key_name value
取值语句 get key_name
删除语法 del key_name
修改原来的值 getset key_name value(新)
获取已有K追加数据 append key_name value
获取k的数据长度 strlen key_name
命令行的编写博主是在linux下的redis环境下测试的,如果环境没有搭建好的小伙伴可以看看博主的redis安装那篇文章
批量操作
批量读 mset k1 v1 k2 v2 ...
批量写 mget k1 k2 ...
设置多个值,但是如果其中有相同的key会设置不成功(原子性,一个失败都失败)
msetnx k1 v1 k2 v2 ...
删除所有key+查询所有key的值
删除当前数据库中的所有key flushdb
删除所有数据库中的key flushall
查询所有的key值 keys *
对数字value的操作
自增、自减
为当前数值+1 incr key_name
为当前数值-1 decr key_name
步长 为当前数值+步长 incrby key_name
步长 为当前数值-步长 decrby key_name
截取字符串
截取范围字符串 getrange key_name 起始位置 终止位置
指定位置添加数据
从哪个位置插入数值 setrange key_name 添加的位置 添加的值
设置过期时间
设置键值的同时,设置过期时间,单位秒 setex key_name 过期时间 value
查看还剩多少秒,-2表示已经过期,-1表示不会过期 ttl key_name
过期后key会被回收,redis中将没有这个key了
应用场景
- 用于保存单个字符串或者JSON字符串数据
- 可以把一个图片文件的内容作为字符串来存储
- 计数器(常规key-value缓存应用。常规计数:微博数、粉丝数)
数据结构
String的数据结构为简单动态字符串。是可以修改字符串的,内部结构类似java的ArrayList,采用预分配冗余空间的方式来减少内存的频繁分配(指的value的结构)
List(列表)
- value的存储是单键多值
- Redis列表是简单的字符串列表,按照插入顺序。你可以去添加一个元素到列表的头部(左边)和尾部(右边)
常用命令
存入列表值
从左边/右边插入一个或者多个值 lpush/rpush key_name v1 v2 v3 ...
从左边存入值
redis的索引下标的起始位置0
0 ~ -1表示取出所有值
右边的存值就是与之相反
从右边存入值
取出列表值(删除)
从左边/右边取出一个值 lpop/rpop key_name
值在键在,当所有的值都被取出时,键就会被销毁了
repoplpush
取出key1列表的右边的一个元素,存入到key2列表左边
rpoplpush key1 key2
这样k1中的最右端元素被取出,放入到k2的最左端位置上,k1中没有这个元素了
获取列表的值
按照索引下标获取元素(从左到右) lrange key_name 起始位置 终止位置
获取索引位置的值 lindex key_name 索引下标
获取列表长度
获取列表长度 llen key_name
在列表中插入新值
在原有值的前面或是后面添加新值 linsert key_name before/after 原有值 新值
删除列表中的值
从左边删除n个value值 lrem key_name n value
列表中元素的替换
在指定索引位置替换新值 lset key_name 索引下标 新值
应用场景
1. 对数据量大的集合数据删减:列表数据显示、关注列表、粉丝列表、留言评价等…分页、热点新闻(TOP5)等
2. 任务队列(通常用来实现一个消息队列,而且可以确保先后顺序)
数据结构
- List的数据结构为快速链表quickList
- 在列表元素较少的情况下会使用一块连续的内存存储,这个结构是ziplist,也即是压缩列表。它会将所有元素紧挨着一起存储,分配一块连续的内存,当数据量比较多的时候才会改成quicklist
- redis将链表和ziplist结合组成quicklist.就是ziplist使用双向指针串起来。这样既能满足快速的插入和删除功能,又不会出现太大的冗余
Set(集合)
- set对外提供的功能与list类似是一个列表的功能,特殊之处在于set是可以自动排重的,当我们需要存储一个列表数据,又不希望出现重复数据时,set是一个很好的选择,并且set提供了判断某个成员是否在一个set集合内的重要接口,这也是list不能提供的
- Redis的Set是String类型的无序集合,它的底层其实是一个value为null的hash表,所以添加,删除,查找的复杂度都是O(1)
单个集合常用命令
添加数据
为一个键添加多个值 sadd key_name v1 v2 v3 ...
取出key中的所有值 smembers key_name
判断是否存在值
判断key中是否存在该值 sismember key_name value
存在返回1,不存在返回0
返回元素个数
返回集合中元素个数 scard key_name
删除集合中的元素
删除集合中key的值(可以删除单个,也可以删除多个)
srem key_name v1
srem key_name v1 v2 ...
当元素都删除完后也会像list一样key值消失
随机获取一个值,然后删除该值
从集合中随机获取一个值 spop key_name
这个也是当数据取完时,键消失
随机获取n个值,不从集合删除值
从指定的键中随机取出n个值 srandmember key_name n
多个集合常用命令
将一个集合的值移到另一个集合
将k1的value传递给k2 smone k1 k2 value
因为set是不能重复的集合,所以如果移过来的值有重复的也只会显示一个,不会添加,但是原来移出值的那个key该值会删除
交集
取出两个集合中的交集元素 sinter k1 k2
并集
取出两个集合的并集元素 sunion k1 k2
差集
取出集合中k1有的k2没有的数据 sdiff k1 k2
使用场景
对两个集合间的数据进行交集、并集、差集运算
数据结构
- Set数据结构是dict字典,字典使用哈希表实现的。
- java中的HashSet内部实现使用的是HashMap,只不过所有的value都指向同一个对象。Redis的set结构也是一样,他的内部也是使用hash结构,所有的value都是指向同一个内部值
Hash(哈希)
- Redis hash是一个键值对集合 Redis
- hash是一个String类型的field和value的映射表,hash特别是适用于存储对象
- 类似Java中的Map<String,Object>
常用命令
添加数据
设置key的单个值(值为hash键值对<field><value>) hset key <field><value>
设置key的多个值 hset key <field><value> <field><value> <field><value> ....
查看数据
从集合field取出value hget key field
如果存入的是中文可能会出现编码错误,会有二进制符号
判断field是否存在
判断field是否存在于key中 hexists key field
存在返回1,不存在返回0
查看hash中的所有field
查看key中的所有field hkeys key
查看hash中的所有value
查看key中的所有value值 hvals key
对数值field进行加、减
为hash表key中的域field的值进行加/减操作
hincrdy key field +值 -值
为最后的数字设置正负就是加减的操作
添加不存在的field的value
为hash表的key域中不存在的field设置value,如果存在设置失败
hsetnx key <field><value>
如果key的域中存在想添加的field将添加不成功返回0,如果不存在则value设置成功返回1
使用场景
1.常用于存储一个对象
2. 分布式Session
数据结构
Hash类型对应的数据结构有两种:ziplist(压缩列表)、hashtable(哈希表)。当filed-value长度较短且个数较少时,使用ziplist,否则使用hashtable
Zset(有序集合 sorted set)
- redis有序集合zset与set非常相似,是一个没有重复元素的字符串集合
- 不同之处在于有序集合的每个成员关联着一个评分(score),这个评分被用来按照从最低分到最高分的方式排序集合中的成员。集合的成员是唯一的,但是评分可以是重复的
- 因为元素是有序的,所以你也可以很快的根据评分( score )或者次序( position )来获取一个范围的元素。
- 访问有序集合的中间元素也是非常快的,因此你能够使用有序集合作为一个没有重复成员的智能列表。
常用命令
添加元素
将一个或者多个member元素及其socre值加入到有序集key当中
zadd key <score1><value1> <score2><value2> ....
查询
返回有序集key中,下标<start><stop>之间的元素
zrange <key><start><stop> [withscores] (可选)
在查询的途中会自动排序
还可以加上withscores值,显示score值
返回有序集key中,所有score值介于min和max之间(包括等于min或max)的成员。有序集成员按score值递增(从小到大)次序排序
zrangebyscore key min max [withscores]
同上,改为从大到小排序
zrevrangebyscore key min max [withscores]
修改
为元素的score加上增量
zincrby key increment value
删除
删除该集合下,指定值的元素
zrem key value
统计
统计该集合,分数区间内的元素个数
zcount key min max
返回排名
返回该值在集合中的培明,从0开始
zrank key value
使用场景
排行榜(畅销排名,积分排名等)
数据结构
zset底层使用了两个数据结构
- hash,hash作用就是关联元素value和权重score,保障元素value的唯一性,可以通过元素value找到对应的score值
- 跳跃表,跳跃表的目的在于给元素value排序,根据score的范围获取元素列表
跳跃表(跳表)
会间隔一个元素然后再查找元素,如果跳到的位置小于查找元素,继续查找,如果跳到的元素大于查找元素,返回来查找,这相比链表的一个一个查找是要节省效率的
结束语
兄弟们,今天的内容到这里也就分享完毕了,其实这只是介绍了redis的五种很常见的数据类型,其实在redis6的版本下已经不单单只是有这五种类型了,如果有兴趣的小伙伴可以去了解一下,同时也希望我的文章能带给正在学习的兄弟一点帮助,好的,话不多说散会,redis后面还会慢慢更新