博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Redis
阅读量:4685 次
发布时间:2019-06-09

本文共 10239 字,大约阅读时间需要 34 分钟。

Redis

Redis是一个开源的使用ANSI C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。从2010年3月15日起,Redis的开发工作由VMware主持。从2013年5月开始,Redis的开发由Pivotal赞助。

# 操作系统:CentOS 6.8# Redis 版本:redis-3.2.5# 虚拟机网路:Nat模式

0 安装

​ 访问或 下载对应版本的Redis。

1481652-20190616234057340-103826445.png

0.1 解压

​ 解压下载的tar包

tar -zxcf redis-3.2.5.tar.gz

1481652-20190616234119111-311636759.png

安装C、C++支持

yum install -y gcc gcc-c++

1481652-20190616234146928-880719198.png

​ 进入解压后的目录中的src目录执行make && make install命令

1481652-20190616234154417-1515348971.png

0.2 启动

​ 进入解压的目录,执行redis-server命令

1481652-20190616234201309-895976719.png

​ 使用redis-server [配置文件位置]即可启动一个redis的数据库,命令默认为当前目录下的配置文件redis.conf 命令可以在任意目录执行,当启动时需要指定配置文件。

0.3 连接

​ 使用redis-cli命令即可连接已启动的redis数据库。

1481652-20190616234212385-1772448860.png

1 基本命令

1.1 启动命令

redis-server  redis.conf 启动命令  后跟配置文件位置redis-cli -p 6379 默认端口为6379

1.2 数据库基本操作

redis-cli -p 6379 进入数据库select [num]      选择库DBSIZE            查看key数量FLUSHDB           清空当前库FLUSHALL          清空所有库默认端口6379 默认16个库

1.3 五大数数据类型

String

  • 基本数据类型,一个key对应一个value
  • 二进制安全,可以包含任何数据(图片或序列化对象)
  • 最大值为512M

Hash

  • 键值对集合
  • String类型的field和value的映射表,适合存储对象
  • 类似Java中的 Map<String,Object>

List

  • 简单的字符串列表,按照插入顺序排序。
  • 可以添加元素到头部或尾部
  • 底层为链表

Set

  • 无序无重复集合
  • 通过底层为HashTable

Zset

  • sorted set
  • 每个元素关联一个double类型的分数排序

1.4 常用命令

​ key

keys *#查看所有keyexists [key_name]#判断key是否存在move   [key_name] [db_num]#移动key到某个库expire [key_name] [时间s]#设置key过期时间 单位秒ttl    [key_name]#查看过期时间type   [key_name]#查看key类型

​ String

set/get/del/append/strlen#数据操作Incr/decr/incrby/decrby#自增自减 自增自减某值 数字getrange/setrange#设置/获取子串setex 
#设置过期时间sentnx#避免覆盖添加值mset/mget/msetnx#批量设置获取(重复失效)

​ List

Lpush/Rpush/Lrange #左右进入\查看 左栈右队 Lpop/rpop #出栈\出队 Lindex #按照索引获取 Llen #获取长度 Lren key [n] [value] #删除多个值 Ltrim key #截取子串 Rpoplpush [list_org] [list_dist] #出队压栈 Lset key index value #给某位置赋值 Linsert key befor/after "" #在某字符前/后插值

​ Set

sadd                                #不重复/重复自动去除smemebers                       #查看集合所有元素sismember                           #检测是否为成员scard                               #获取集合元素个数srem key value                      #删除元素srandmember key int                 #随机出N个整数spop key                            #随机出栈smove key1 key2                     #随机出一个值给集合sdiff/sinter/sunion                 #差集/交集/并集

​ Hash

hset/hget/hmset/hmget/hgetall/hdel  #获取添加移除单个/多个customer:        id: 11        name: Lee        age: 20hmset customer id 11 name Lee age 20hle                                 #获取长度hexists key                         #获取某个keyhkeys/hvals                         #获取键\值hincrby/hincrbyfloat                #自增某个值hstnx                               #避免覆盖插值

​ Zset

zadd/zrange                         #添加/查看zdd zset 1 v1 2 v2 3 v3zrangbyscore [begin_s] [end_s]      #区域查看(不包含 limitzrem key                            #删除某个值zcard/zcount                        #统计个数zrank                               #取值的下表zscore                              #取值的分数zrevrank                            #取下标zrevrangezrevrangebyscore                    #结束分数到开始分数

1.5 配置文件

#守护进程方式daemonize yes#默认写入pidpidfile /var/run/redis_6379.pid#默认端口port 6379# include /path/to/other.confbind 127.0.0.1#超时关闭连接timeout 0#日志级别# Specify the server verbosity level.# This can be one of:# debug (a lot of information, useful for # development/testing)# verbose (many rarely useful info, but not a mess like the # debug level)# notice (moderately verbose, what you want in production  # probably)# warning (only very important / critical messages are # logged)loglevel notice# output for logging but daemonize, logs will be sent to # /dev/nulllogfile ""#默认数据库数量databases 16#同步数据文件save 
#默认提供三个条件 1 in 900s 10 in 300 1000 in 60save 900 1save 300 10save 60 10000#缓存级别# volatile-lru -> Evict using approximated LRU among the # keys with an expire set.# allkeys-lru -> Evict any key using approximated LRU.# volatile-lfu -> Evict using approximated LFU among the # keys with an expire set.# allkeys-lfu -> Evict any key using approximated LFU.# volatile-random -> Remove a random key among the ones with# an expire set.# allkeys-random -> Remove a random key, any key.# volatile-ttl -> Remove the key with the nearest expire# time (minor TTL)# noeviction -> Don't evict anything, just return an error# on write operations.# maxmemory-policy noeviction#数据库路径dir ./#默认密码# requirepass foobared#默认最大连接数# maxclients 10000#最大内存# maxmemory

2 持久化

2.1 RDB(Redis Database)

在指定时间间隔内将内存中的数据集快照写入磁盘中即Snapshot快照,恢复时直接将快照导入内存。持久化由Fork进程进行,主进程不进行IO擦破做,对数据完整性不敏感,最后一次持久化的数据可能丢失。Fork为原进程的复制,所有数据与原进程完全一致,并作为原进程的子进程。保存形式为 dump.rdb配置
############### SNAPSHOTTING ############################ Save the DB on disk:##   save 
# In the example below the behaviour will be to save:# after 900 sec (15 min) if at least 1 key changed# after 300 sec (5 min) if at least 10 keys changed# after 60 sec if at least 10000 keys changed## Note: you can disable saving completely by commenting# out all "save" lines.## It is also possible to remove all the previously # configured save# points by adding a save directive with a single empty # string argument like in the following example:# save "" #save 命令可手动保存(阻塞式) bgsave 异步不阻塞# 在设置时间内改动后自动分片存储,触发快照,备份文件自动恢复save 900 1save 300 10save 60 10000#恢复文件位置dir ./#默认恢复文件# The filename where to dump the DBdbfilename dump.rdb#数据一致性stop-writes-on-bgsave-error yes#压缩算法使用rdbcompression yes#数据校验(为增加性能可关闭 不推荐关闭)rdbchecksum yes

优点:适合大规模的数据恢复,对数据完整性和一致性要求不高

缺点:意外宕机只有最后一次快照,fork进程导致两倍程序消耗


2.2 AOF(Append Only File)

通过日志的形式记录每个写操作。
#默认关闭appendonly no#默认文件名appendfilename "appendonly.aof"# Redis supports three different modes:## no: don't fsync, just let the OS flush the data when it # wants. Faster. #不设置# always: fsync after every write to the append only log.# Slow, Safest.  #总是使用# everysec: fsync only one time every second. Compromise.# The default is "everysec" #默认。appendfsync everysec#重写时运用appendsyncno-appendfsync-on-rewrite no#重写比例和重写日志大小auto-aof-rewrite-percentage 100auto-aof-rewrite-min-size 64mb #通常3GB+

优点:每秒同步 修改同步 不同步

缺点:恢复速度慢 存储空间大


推荐使用两种共用,启动时优先载入AOF备份,AOF数据丢失不超过2秒的数据


3 事务

串行执行一组命令,命令会被序列化,不许阻塞,即一个事务。没有隔离级别的概念,不保证原子性,没有回滚,部分支持事务。

3.1 基本命令

DISCARD                 放弃事务EXEC                    执行事务块MULTI                   标记开始UNWATCH                 取消监视所有键WATCH KEY [key ...]     开启监视

3.2 事务使用步骤

MULTI                //开启事务,返回OKOperationes     //入队不操作,返回QUEUE,出现错误直接取消EXEC/MULTI  //执行或取消执行,单个语句出错,其他可以执行

3.3 WATCH监控

悲观锁:如表级锁,当修改时加锁,其他修改无法执行(高一致,低并发)乐观锁:不锁+版本号 在修改时读取版本号,执行修改时版本号>=读取时版本CAS:即compare and swap 或者 compare and set,涉及到三个操作数,数据所在的内存值,预期值,新值。当需要更新时,判断当前内存值与之前取到的值是否相等,若相等,则用新值更新,若失败则重试,一般情况下是一个自旋操作,即不断的重试。

WATCH使用步骤

WATCH balance    MULTL    Operations    EXEC    //乐观锁已经被修改的版本将无法执行事务     //执行后锁已被清除    已被修改  -->  UNWATCH取消监控 --> WATCH  -->

4 发布与订阅

进程间的一种消息通信模式:发送者(pub)与订阅者(sub) 主题模式

使用命令

PSBUSCRIBE pattern[pattern ...]         订阅PUBSUB subcommand[arg [arg]]            查看订阅状态PUBLISH channel message                 发布消息到主题PUNSUBSCRIBE pattern                    取消订阅SUBSCRIBE channel[channel ...]          订阅多个UNSUBSCRIBE[channel[channel]]           退订多个

使用步骤

订阅消息即进入消息监听状态,消息发布时自动接收消息发布者发布消息到对应频道,消息监听处即受到消息

5 主从复制

5.1 配置方法

info replication            查看数据库信息SLAVEOF IP Port             隶属于主机

5.2 info replication

#从机role:slavemaster_host:127.0.0.1master_port:6379#主机role:masterconnected_slaves:2slave0:ip=127.0.0.1,port=6381,state=online,offset=1321,lag=0slave1:ip=127.0.0.1,port=6380,state=online,offset=1321,lag=1#主机可读可写、从机可读不可写#只需要在从机上使用命令SLAVEOF IP port 命令即可#从机可以访问所有缓存中数据 主机宕机后可重开 从机依旧 反之不行
中心化配置,主机宕机系统瘫痪,从机宕机需要重新配置,一主二从。

5.3 SLAVEOF no one

将从机转换为主机,从机需要重新配置

5.4 复制原理

首次全量复制,而后增量复制,重连全量复制。

5.5 哨兵模式

创建`sentinel.conf`配置文件,加入哨兵监视器
sentinel monitor host-main 127.0.0.1 6379    1                 监视名        IP      端口   票数
命令启动:`redis-sentinel sentinel.conf`自动监视,当主机宕机自动选举主机,原主机恢复后自动设置为从机待机

缺点: 有延迟,当系统使用高时,延迟现象比较严重


6 创建集群

6.1 配置文件修改

​ 将解压目录中的redis.conf文件复制一份到存放集群配置文件的目录(任意目录中),并创建集群中的每一个数据库的配置文件(新建文件)。

1481652-20190616234230324-101339908.png

​ 修改配置文件中集群相关的参数,将配置设置为集群模式,以目录中的redis-6379.conf为例如下书写。

include /opt/software/redis/cluster/configure/conf/redis.conf# 引入默认配置文件port 6379# 端口号指定dir /opt/software/redis/cluster/configure/dbdump# dump 文件目录指定dbfilename dump-6379.dump# dump文件名称指定pidfile /var/run/redis_6379.pid# 指定piddaemonize yes# 守护进程(后台运行)logfile /opt/software/redis/cluster/configure/log/redis-6379.log# 日志存放目录cluster-enabled yes# 集群开启cluster-config-file nodes-6379.conf# 集群配置文件名称cluster-node-timeout 15000# 集群超时时间

6.2 安装ruby支持

​ 执行yum install ruby rubygems -y安装ruby支持。

​ 需要redis-3.2.0.gem包,

​ 在gem包所在目录执行gem install --local redis-3.2.0.gem命令

6.3 启动集群

6.3.1 启动redis

redis-server /opt/software/redis/cluster/configure/conf/redis-6379.confredis-server /opt/software/redis/cluster/configure/conf/redis-6380.confredis-server /opt/software/redis/cluster/configure/conf/redis-6381.confredis-server /opt/software/redis/cluster/configure/conf/redis-6389.confredis-server /opt/software/redis/cluster/configure/conf/redis-6390.confredis-server /opt/software/redis/cluster/configure/conf/redis-6391.conf

6.3.2 查看启动

1481652-20190616234243863-1491071842.png

​ 所有启动中的服务均为cluster即启动成功

6.3.3 组成集群

​ 进入redis解压目录中的src文件夹,执行命令

./redis-trib.rb create --replicas 1 192.168.111.3:6379 192.168.111.3:6380 192.168.111.3:6381 192.168.111.3:6389 192.168.111.3:6390 192.168.111.3:6391

​ 出现下图即创建成功。

1481652-20190616234253203-629467623.png

redis-cli -c ...注意连接时需要添加一个-c参数。

7 Java中使用

Jedis jedis = new Jedis(url,port);//事务Transaction transaction = jedis.multi();transaction.set();   ...transaction.discard();  //取消执行//开启watchint now;jedis.watch("key");int value = Integer.paraseInt(jedis.get("key"));if(value < now){  jedis.unwatch();  soutp("redo");  return false}else{  Transaction tr = jedis.multi();  transaction.method("","");  transaction.exex()}jedis.unwatch();//主从复制Jedis jedis_master = new Jedis(url,port);Jedis jedis_salve  = new Jedis(url,port);//主从复制 读写分离jedis_salve.slaveof(url,port);jedis_master.set(...);String result = jedis_salve.get(...);//JedisPoolpublic class JedisPoolUtil{    private static volatile JedisPool jedisPool = null;    private JedisPoolUtrl(){}    public static JedisPool getJedisPoolInstance()    {      if(null == jedisPool)      {        synchronized (JedisPoolUtil.class)        {          if(null == jedisPool)          {        JedisPoolConfig poolConfig = new JedisPoolConfig();            poolConfig.set(...);        jedisPool = new JedisPool(poolConfig,url,port);        return JedisPool;          }        }      }          }    public static voie relase(JedisPool jedisPool,Jedis jedis)  {    if(null != jedis)    {      jedisPool.returnResourceObject(jedis);    }  }}

转载于:https://www.cnblogs.com/Wu-Zang/p/9607404.html

你可能感兴趣的文章
函数的复写
查看>>
17_重入锁ReentrantLock
查看>>
winform窗口关闭提示
查看>>
64款工具,总有合适您的那款
查看>>
我的第一篇博客
查看>>
大数据学习线路整理
查看>>
【C++算法与数据结构学习笔记------单链表实现多项式】
查看>>
关于ProjectServer定制化项目中心页面
查看>>
使用Collectd + InfluxDB + Grafana进行JMX监控
查看>>
Linux下tar,zip命令详解
查看>>
C#垃圾回收机制
查看>>
31、任务三十一——表单联动
查看>>
Jenkins之Linux和window配置区别
查看>>
python之hasattr、getattr和setattr函数
查看>>
maven使用阿里镜像配置文件
查看>>
iOS开发UI篇—UITableview控件使用小结
查看>>
lesson1 预备知识
查看>>
Copy code from eclipse to word, save syntax.
查看>>
arguments.callee的作用及替换方案
查看>>
23 Java学习之RandomAccessFile
查看>>