redis学习
- 前言
- 一、redis是什么?
- 二、redis的能干嘛?
- 三、redis的特性
- 四、redis安装(linux环境)
- 1.下载安装包
- 2.上传到linux服务器,解压压缩包
- 3. 进入解压后的文件下,安装c环境
- 4.配置文件
- 5.启动服务
- 五、redis自带压测包 redis-benchmark
- 六、redis五大数据类型
- String类型
- List类型
前言
当前的技术环境下,太多的技术,让我们看的眼花缭乱。高速的开发工作下,我们似乎忘记的学习技术的本身,往往是为了解决问题的目的,而忘记了产生问题的原因,以及解决方法的底层。浮躁的我们,遵循了鲁迅先生说的“拿来主义”,解决完问题便抛之脑后,却忽视了知其然还要知其所以然的主旨。你说redis我们用过没,当然用过!会用吗?会还是不会,我却犹豫了。只做了简单的存和取,算是会了吗?为了解决这些问题,在这个快的年代里,我开始让自己慢起来,慢下来学习redis。从头进行学习理解。
一、redis是什么?
Redis(Remote Dictionary Server ),即远程字典服务,是一个开源的使用ANSI C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。
免费、开源,是当下热门的NoSql技术之一。
读每秒100000+ 写每秒80000+
二、redis的能干嘛?
内存储存、持久化,内存中是断电即失的,所以说持久化很重要(rdb,aof)
效率高,可用用于高速缓存
可以做发布订阅系统
地图信息分析
计时器、计数器 (点赞数、浏览量)
三、redis的特性
多数据结构
持久化
集群
支持事务
四、redis安装(linux环境)
1.下载安装包
wget https://download.redis.io/releases/redis-6.0.8.tar.gz
2.上传到linux服务器,解压压缩包
[root@iZ2ze2nmkl044m4m0cgk5kZ opt]# tar -zxvf redis-6.0.8.tar.gz
3. 进入解压后的文件下,安装c环境
yum install gcc-c++ #安装c换件
make #将需要的文件编译起来
make install #检查一下是否安装完成
4.配置文件
将 /opt/redis-6.0.8/redis-conf 文件备份到/usr./local下
[root] cp /opt/redis-6.0.8/redis.conf /usr/local/bin/mconfig/
修改配置文件 daemonize 改为 yes
cd /usr/local/bin/mconfig
vim redis.conf
5.启动服务
通指定的配置文件启动服务
redis-server mconfig/redis.conf
启动redis客户端启动服务
redis-cli -p 6379 #启动客户端
keys * #查询数据库0的所有key
查看redis 服务是否启动着
ps -ef | grep redis
关闭redis服务
redis-cli -p 6379 #链接到客户端
shutdown #关闭服务
五、redis自带压测包 redis-benchmark
redis-benchmark 是redis自带的并发压测工具
#测试:100个并发 10000次请求
redis-server mconfig/redis.conf #指定文件启动redis
redis-benchmark -h localhost -p 6379 -c 100 -n 10000 #100个并发 10000次请求
数据分析
六、redis五大数据类型
String类型
常用命令
set key value // 插入键值
get key //根据键获取值
append key value //在指定的键里追加值
strlen key //获取键值的长度
keys * //获取当前数据库的key
incr key //自增1
decr key //自减1
incrby key number //按照设置的不常自增
decrby key number //按照设置的步长自减
getrange key star end //按照范围截取字符串,并替换原有值
setrange key star value //在指定位置开始替换字符串值
setex key number value //插入值,并设置有效时间
setnx key value //如果不存在这个key 则插入,否则插入失败
*字符串set值*
127.0.0.1:6379> set key1 'hello' #设置值
OK
127.0.0.1:6379> get key1 #获取值
"hello"
127.0.0.1:6379> APPEND key1 ' world'#往key1里追加值,append
(integer) 11 #返回字符长度
127.0.0.1:6379> get key1 #获取值
"hello world"
127.0.0.1:6379> STRLEN key1 #strlen 获取值得长度
(integer) 11
127.0.0.1:6379>keys * #查询当前数据库中所有键
1) "key1"
127.0.0.1:6379> APPEND key 'xiaoye' #往key里面追加值,如果这个键不存在,则等于新建set值
(integer) 6
127.0.0.1:6379> keys * #获取所有键
1) "key"
2) "key1"
127.0.0.1:6379> get key #获取值
"xiaoye"
127.0.0.1:6379>
############################################################################
*redis中执行i++操作,一般用于浏览量、点赞数(计数器)*
127.0.0.1:6379> FLUSHDB #flushdb 清空当前数据库,flushall 清空所有数据库
OK
127.0.0.1:6379> keys * #获取当前数据库所有的键
(empty array)
127.0.0.1:6379> set views 0 #设置浏览量0
OK
127.0.0.1:6379> get views #获取浏览量
"0"
127.0.0.1:6379> INCR views #自增一 i++ incr
(integer) 1
127.0.0.1:6379> DECR views #自减一 i-- decr
(integer) 0
127.0.0.1:6379> INCRBY views 10 #自增10 设置步长
(integer) 10
127.0.0.1:6379> DECRBY views 10 #自减10 设置步长为10
(integer) 0
127.0.0.1:6379>
############################################################################
*字符串 范围 getranage*
127.0.0.1:6379> set key1 'xiaoye,number one' #设置字符串
OK
127.0.0.1:6379> get key1 #获取值
"xiaoye,number one"
127.0.0.1:6379> GETRANGE key1 0 4 #截取0到4的字符串,相当于subString
"xiaoy"
127.0.0.1:6379> GETRANGE key1 0 5
"xiaoye"
127.0.0.1:6379> GETRANGE key #截取不存在的键,则会报错
(error) ERR wrong number of arguments for 'getrange' command
127.0.0.1:6379> GETRANGE key1 0 -1 #截取全部的值 -1 和 get 一样
"xiaoye,number one"
############################################################################
*替换 setrange*
127.0.0.1:6379> get king
"xiaoye,number one"
127.0.0.1:6379> SETRANGE king 0 'xiaoya' #从第0个位置开始替换键的值
(integer) 17
127.0.0.1:6379> get king
"xiaoya,number one"
127.0.0.1:6379>
############################################################################
*设置过期时间*
setex (set with expire) #设置键的过期时间
setnx (set if not exist) #如果键不存在,则创建键(一般用于分布式锁)
127.0.0.1:6379> SETEX temp 30 'study redis' #设置键30秒过期
OK
127.0.0.1:6379> get temp #获取键值
"study redis"
127.0.0.1:6379> get temp #过期后获取键值
(nil) #表示不存在
127.0.0.1:6379> SETNX name '123' #如果不存在则设置键
(integer) 1 #返回1 设置成功
127.0.0.1:6379> setnx name '456' #如果存在,则不进行创建或者覆盖
(integer) 0 #返回0 设置失败
127.0.0.1:6379> get name #获取键值
"123"
127.0.0.1:6379> setnx temp '789' #设置过期后的键
(integer) 1
127.0.0.1:6379> get temp #获取后发现,设置成功
"789"
127.0.0.1:6379> EXISTS temp #判断键是否存在 exists
(integer) 1
############################################################################
批量存取值 mset mget (maney get /set)
127.0.0.1:6379> msetnx key1 value2 key2 value2 key3 value3 #批量设置键值 存在则不创建
(integer) 1
127.0.0.1:6379> keys * #获取所有键
1) "key3"
2) "key2"
3) "key1"
127.0.0.1:6379> msetnx key1 123 key4 value4 #批量设置键值时,有存在的键时
#则不进行创建,统一成功或者失败
#体现了批量设值的原子性
(integer) 0
127.0.0.1:6379> keys *
1) "key3"
2) "key2"
3) "key1"
127.0.0.1:6379> mget key1 key2 key3 #批量获取键中的值
1) "value2"
2) "value2"
3) "value3"
############################################################################
设置对象
127.0.0.1:6379> msetnx user:1:name 'zhangsan' user:1:age 24 #user:1:name 当做键
#user:1:age 当做键
#user:1 id体现为1
(integer) 1
127.0.0.1:6379> get user:1 #直接get user:1 是获取不到值的
(nil) #因为其本身就不是一个对象
127.0.0.1:6379> mget user:1:name user:1:age #还需要批量获取键值
1) "zhangsan"
2) "24"
############################################################################
getset 先获取值,然后set新的值,返回旧值
127.0.0.1:6379> getset user 'zhangsan' #如果获取的值为空时,返回null,并把新的值赋进去
(nil)
127.0.0.1:6379> set user 'zhangsan'
OK
127.0.0.1:6379> getset user 'lisi' #如果获取的值不为空,则返回值,并摄入新值
"zhangsan"
127.0.0.1:6379> get user
"lisi"
############################################################################
String类型的应用场景:
1.计数器
2.使用多场景的数据统计 (以用户为维度的多数据的统计,粉丝数、点赞数的等)
List类型
List基础命令
Lpush key [values] 往list里面插入值,一次可以插入多值
Rpush key [values] 从右边开始插入值,可插多值
Lrange key start end 获取list中的值 必须要有区间 取值也是倒叙的,从左边第一个开始取 只能从左边取
Lpop key 移除list里面的值,有且只能移除最外层的一个值。返回被移除的值
Lpop key 从右边开始移除值,返回被移除的值
Lindex key index 通过下标获取list里的值
Llen key 获取list的长度
Lrem key count value #移除几个指定的值
ltrim key star end #通过下标截取指定的元素,并替换现在的数组、
rpoplpush #移除最后一个值,并添加在新数组中
lset key index item #通过下标,更新数组中的值
Linsert key before item value #在指定元素前或者后,插入具体的值
插入值
127.0.0.1:6379> flushdb #清空数据库
OK
127.0.0.1:6379> Lpush list one two thess #push值到集合里
(integer) 3
127.0.0.1:6379> LRANGE list 0 -1 #lrange 从左边还是获取所有值
1) "thess"
2) "two"
3) "one"
127.0.0.1:6379> rpush list frist seconed #从右边push 值到集合里
(integer) 5
127.0.0.1:6379> LRANGE list -1 #只能从左边获取,右边获取报错
(error) ERR wrong number of arguments for 'lrange' command
127.0.0.1:6379> LRANGE list 0 -1 #获取所有值
1) "thess"
2) "two"
3) "one"
4) "frist"
5) "seconed"
127.0.0.1:6379> lpop list #从左边删除一个值
"thess"
127.0.0.1:6379> lpop list 1 #只能删除最外面的值,无法指定下标删除
(error) ERR wrong number of arguments for 'lpop' command
127.0.0.1:6379> rpop list #从右边删除第一个值
"seconed"
127.0.0.1:6379> LRANGE list 1 #Lrange 必须要有区间来获取
(error) ERR wrong number of arguments for 'lrange' command
127.0.0.1:6379> LRANGE list 0 -1 #获取所有的值
1) "two"
2) "one"
3) "frist"
#####################3########################
lindex 获取指定的值
127.0.0.1:6379> LINDEX list 1 #从左边开始获取下标为一的值
"one"
127.0.0.1:6379> LLEN list #获取list的长度
(integer) 3
127.0.0.1:6379>
Lrem 移除指定的值
127.0.0.1:6379> LREM list 1 one
(integer) 1
127.0.0.1:6379> LRANGE list 0 -1
1) "two"
2) "frist"
#####################################################
rpoplpush #移除数组中最后一个值,并添加到一个新数组中
127.0.0.1:6379> LRANGE list 0 -1
1) "two"
2) "frist"
127.0.0.1:6379> RPOPLPUSH list newlist
"frist"
127.0.0.1:6379> LRANGE list 0 -1
1) "two"
127.0.0.1:6379> LRANGE newlist 0 -1
1) "frist"
127.0.0.1:6379>
###################################################
ltrim 截取指定的长度
127.0.0.1:6379> lpush list xiaoye #插入数据
(integer) 2
127.0.0.1:6379> LPUSH list xiaoya #插入数据
(integer) 3
127.0.0.1:6379> lrange list 0 -1 #获取数据
1) "xiaoya"
2) "xiaoye"
3) "two"
127.0.0.1:6379> ltrim list 1 2 #通过下标截取数据
OK
127.0.0.1:6379> LRANGE list 0 -1 #覆盖了原数组
1) "xiaoye"
2) "two"
###################################################
127.0.0.1:6379> LRANGE list 0 -1
1) "xiaoye"
2) "number one"
127.0.0.1:6379> LINSERT list before xiaoye hello #在指定元素前插入元素
(integer) 3
127.0.0.1:6379> LRANGE list 0 -1
1) "hello"
2) "xiaoye"
3) "number one"
127.0.0.1:6379> LINSERT list after 'number one' world #在指定元素后,插入值
(integer) 4
127.0.0.1:6379> LRANGE list 0 -1
1) "hello"
2) "xiaoye"
3) "number one"
4) "world"
小结
- list其实就是一个链表。可以从左边、右边插入 获取值
- 如果key不存在,则会创建一个新的链表
- 如果key存在,则会在链表里插入值
- 链表从两边操作,新增或修改值效率高一些。操作中间的值,效率相对低一些。
- 可以作:消息队列(Lpush Rpop) 栈(Lpush Lpop)使用