zoukankan      html  css  js  c++  java
  • Redis学习1

    Redis能干嘛

    1. Redis 官方数据 11W/秒读,8W/秒写,效率高
    2. 周期性的将数据写入磁盘做持久化。有两种方式:RDB、AOF
    3. 发布订阅系统,可以做消息队列
    4. 地图信息分析
    5. 计时器、计数器(浏览量)

    特性

    1. 多样的数据类型
    2. 持久化
    3. 集群
    4. 事务

    Redis基础知识

    1. Redis默认有16个数据库 ,默认第0个数据库,可以使用Select 命令切换 ;DBSize可以查看数据库大小; Keys * 可以查看所有的Key;flushall 清除全部 flushdb清除当前库

    2. Redis是单线程的

      Redis是很快的,Redis是基于内存操作的,CPU不是Redis性能瓶颈Redis的瓶颈是根据机器内存和网络带宽。既然可以使用单线程来实现,所以就使用了单线程。

    3. Redis为什么单线程还这么快

      1. 误区1:高性能的服务器一定是多线程

      2. 误区2:多线程(CPU上下文切换!)一定比单线程快

        CPU速度>内存速度>硬盘速度

        核心:Redis是将所有的数据全部放在内存中的,所以说使用单线程操作效率就是最高的。多线程(上下文切换:操作耗时!!),对于内存系统来说,如果没有上下文切换效率就是最高的!多次读写都是在一个CPU上。

    4. Redis 可以用作数据库,缓存,消息中间件

    Redis-Key

    String

    keys * #查看所有key
    
    Set name Wayne #存值
    
    get name #取值
    
    EXISTS name  #检查name是否存在
    
    move name #移除当前key
    
    EXPIRE name 10 #设置过期时间,单位是秒
    
    TTL name # 查看key的剩余时间
    
    Type name # 查看类型
    
    FlushALL #清空所有库
    
    Append Name Zhang #追加字符串
    ################################################
    incr views # views++
    decr views # views--
    incrby views 10 #views+10
    decrby views 10 #views-10
    ################################################
    #  setex 设置 key 多长时间过期
    127.0.0.1:6379> setex cookie 30 username1
    OK
    127.0.0.1:6379> get cookie
    "username1"
    127.0.0.1:6379> ttl cookie
    (integer) 22
    127.0.0.1:6379> ttl cookie
    (integer) 18
    127.0.0.1:6379>
    #setnx 如果没有才设置,有了就不设置了 (在分布式锁中会用)
    127.0.0.1:6379> setnx ok ok
    (integer) 1
    127.0.0.1:6379> setnx ok notok
    (integer) 0
    127.0.0.1:6379> get ok
    
    ################################################
    # mset 批量设置值
    # mget 批量获取值
    # msetnx 批量存值(如果有已经存在的,全不改)一起成功,一起失败
    127.0.0.1:6379> mset k1 v1 k2 v2
    OK
    127.0.0.1:6379> mget k1 k2
    1) "v1"
    2) "v2"
    127.0.0.1:6379> msetnx k4 v4 k1 v1
    (integer) 0
    127.0.0.1:6379> get v4
    (nil)
    127.0.0.1:6379> msetnx k4 v4 k1 v2
    (integer) 0
    127.0.0.1:6379> get k4
    (nil)
    127.0.0.1:6379> get k1
    "v1"
    ################################################
    # user:{id}:{filed}
    ################################################
    #getset 先获取一个值在set一个值 
    127.0.0.1:6379> getset db redis
    (nil)
    127.0.0.1:6379> getset db mongodb
    "redis"
    127.0.0.1:6379> get db
    "mongodb"
    127.0.0.1:6379>
    
    
    

    String类型使用场景:Value除了是我们的字符串还可以是数字。

    • 计数器

    • 对象缓存存储

    List

    在Redis里面,我们可以把list完成栈、队列、阻塞队列

    ################################################
    # lpush ,从左面push lrange ,取数组 0,-1 取所有 ,rpush,从右面push
    127.0.0.1:6379> lpush list1 1 2 3 4 5
    (integer) 5
    127.0.0.1:6379> lrange list 0 -1
    (empty list or set)
    127.0.0.1:6379> lrange list1 0 -1
    1) "5"
    2) "4"
    3) "3"
    4) "2"
    5) "1"
    127.0.0.1:6379> rpush list1 1 2 3 4 5
    (integer) 10
    127.0.0.1:6379> lrange list1 0 -1
     1) "5"
     2) "4"
     3) "3"
     4) "2"
     5) "1"
     6) "1"
     7) "2"
     8) "3"
     9) "4"
    10) "5"
    ################################################
    # lpop 从左面移除 rpop从右面移除
    127.0.0.1:6379> lpop list1
    "5"
    127.0.0.1:6379> lrange list1 0 -1
    1) "4"
    2) "3"
    3) "2"
    4) "1"
    5) "1"
    6) "2"
    7) "3"
    8) "4"
    9) "5"
    127.0.0.1:6379> rpop list1
    "5"
    127.0.0.1:6379> lrange list1 0 -1
    1) "4"
    2) "3"
    3) "2"
    4) "1"
    5) "1"
    6) "2"
    7) "3"
    8) "4"
    ################################################
    # llen 获取列表长度
    127.0.0.1:6379> llen list1
    (integer) 8
    ################################################
    # lrem 移除指定的值
    127.0.0.1:6379> lrange list1 0 -1
    1) "4"
    2) "3"
    3) "2"
    4) "1"
    5) "1"
    6) "2"
    7) "3"
    8) "4"
    127.0.0.1:6379> lrem list -1 4
    (integer) 0
    127.0.0.1:6379> lrange list1 0 -1
    1) "4"
    2) "3"
    3) "2"
    4) "1"
    5) "1"
    6) "2"
    7) "3"
    8) "4"
    127.0.0.1:6379> lrem list1 10000 4
    (integer) 2
    127.0.0.1:6379> lrange list1 0 -1
    1) "3"
    2) "2"
    3) "1"
    4) "1"
    5) "2"
    6) "3"
    ################################################
    #rpoplpush
    127.0.0.1:6379> lrange list1 0 -1
    1) "3"
    2) "2"
    3) "1"
    4) "1"
    5) "2"
    6) "3"
    127.0.0.1:6379> rpoplpush list1 list2
    "3"
    127.0.0.1:6379> lrange list1 0 -1
    1) "3"
    2) "2"
    3) "1"
    4) "1"
    5) "2"
    127.0.0.1:6379> lrange list2 0 -1
    1) "3"
    ################################################
    #lset 更新值,不存在的index,就报超出索引的err了
    127.0.0.1:6379> lpush list3 1
    (integer) 1
    127.0.0.1:6379> lset list3 1 2
    (error) ERR index out of range
    
    ################################################
    #linsert
    127.0.0.1:6379> lpush list1 1 2 3
    (integer) 3
    127.0.0.1:6379> linsert list1 after 2 100
    (integer) 4
    127.0.0.1:6379> lrange list1 0 -1
    1) "3"
    2) "2"
    3) "100"
    4) "1"
    ################################################
    #trim 修剪,有点像SubString
    127.0.0.1:6379> lrange list1 0 -1
    1) "3"
    2) "2"
    3) "100"
    4) "1"
    127.0.0.1:6379> ltrim list1 2 3
    OK
    127.0.0.1:6379> lrange list1 0 -1
    1) "100"
    2) "1"
    

    小结

    • List实际是链表,Before Node after ,left right 都可以插入值
    • 如果key不存在,创建新的链表
    • 如果key存在,新增内容
    • 如果移除了所有值,空链表,也相当于不存在
    • 在两边插入或者改动效率最高,中间元素效率相对来说低

    消息队列 Lpush Rpop

    栈 Lpush Lpop

    Set(集合)

    set中的值不能重复

    ################################################
    # sadd 添加 ,sismember 检查是否包含, scard 集合个数,smembers 显示所有成员,srem删除成员,sranmember 随机抽出一个数
    127.0.0.1:6379> sadd myset 1
    (integer) 1
    127.0.0.1:6379> sadd myset 2
    (integer) 1
    127.0.0.1:6379> sadd myset 3
    (integer) 1
    127.0.0.1:6379> sismember myset 3
    (integer) 1
    127.0.0.1:6379> sismember myset 5
    (integer) 0
    127.0.0.1:6379> sadd myset 3
    (integer) 0
    127.0.0.1:6379> scard myset
    (integer) 3
    127.0.0.1:6379> smembers myset
    1) "1"
    2) "2"
    3) "3"
    127.0.0.1:6379> srem myset 2
    (integer) 1
    127.0.0.1:6379> smembers myset
    1) "1"
    2) "3"
    127.0.0.1:6379> smembers myset
    1) "1"
    2) "3"
    127.0.0.1:6379> sadd myset 1 2 3 4 5 6 7
    (integer) 5
    127.0.0.1:6379> smembers myset
    1) "1"
    2) "2"
    3) "3"
    4) "4"
    5) "5"
    6) "6"
    7) "7"
    127.0.0.1:6379> srandmember myset
    "6"
    127.0.0.1:6379> srandmember myset 2
    1) "6"
    2) "4"
    ################################################
    #sdiff 取 差集
    #sunion取 并集
    #sinter取 交集
    127.0.0.1:6379> sadd k1 a b c d e
    (integer) 5
    127.0.0.1:6379> sadd k2 b c
    (integer) 2
    127.0.0.1:6379> sdiff k1 k2
    1) "a"
    2) "d"
    3) "e"
    127.0.0.1:6379> smembers k1
    1) "b"
    2) "a"
    3) "d"
    4) "c"
    5) "e"
    127.0.0.1:6379> sadd k2 f
    (integer) 1
    127.0.0.1:6379> sunion k1 k2
    1) "d"
    2) "c"
    3) "b"
    4) "a"
    5) "f"
    6) "e"
    127.0.0.1:6379> sinter k1 k2
    1) "b"
    2) "c"
    

    hash (哈希)

    Map集合,key—map。本质和String没有太大区别

    ################################################
    #hset , hmset ,hget ,hmget ,hgetall ,hdel , hlen
    127.0.0.1:6379> hset myhash field1 hello
    (integer) 1
    127.0.0.1:6379> hmset key myhash f2 v2 f3 v3
    (error) ERR wrong number of arguments for HMSET
    127.0.0.1:6379> hmset myhash f2 v2 f3 v3
    OK
    127.0.0.1:6379> hget myhash f2
    "v2"
    127.0.0.1:6379> hmget f2 f3
    1) (nil)
    127.0.0.1:6379> hmget myhash f2 f3
    1) "v2"
    2) "v3"
    127.0.0.1:6379> hmget myhash f2 f2
    1) "v2"
    2) "v2"
    127.0.0.1:6379> hgetall myhash
    1) "field1"
    2) "hello"
    3) "f2"
    4) "v2"
    5) "f3"
    6) "v3"
    127.0.0.1:6379> hdel myhash f2
    (integer) 1
    127.0.0.1:6379> hgetall myhash
    1) "field1"
    2) "hello"
    3) "f3"
    4) "v3"
    127.0.0.1:6379> hlen myhash
    (integer) 2
    ################################################
    #HEXISTS
    127.0.0.1:6379> HEXISTS myhash f3
    (integer) 1
    ################################################
    #hkeys hvals 获取所有key 获取vals 
    127.0.0.1:6379> hkeys myhash
    1) "field1"
    2) "f3"
    127.0.0.1:6379> hvals myhash
    1) "hello"
    2) "v3"
    ################################################
    #Hincr Hincrby Hdecr Hdecrby
    

    ZSet(有序集合)

    在Set的基础上,增加了一个值,用来排序

    ################################################
    #zadd zadd zrange
    127.0.0.1:6379> zadd zs 1 xiaotang
    (integer) 1
    127.0.0.1:6379> zadd zs 2 xiaona 3 zzy
    (integer) 2
    127.0.0.1:6379> zcard zs
    (integer) 3
    127.0.0.1:6379> zrange zs 0 -1
    1) "xiaotang"
    2) "xiaona"
    3) "zzy"
    ################################################
    #zrangebyscore 升序排序
    127.0.0.1:6379> zrangebyscore zs -inf +inf withscores
    1) "xiaotang"
    2) "1"
    3) "xiaona"
    4) "2"
    5) "zzy"
    6) "3"
    #zrevrangebyscore 降序排序 zrevrange
    127.0.0.1:6379> zrevrangebyscore zs +inf -inf withscores
    1) "zzy"
    2) "3"
    3) "xiaona"
    4) "2"
    5) "xiaotang"
    6) "1"
    127.0.0.1:6379> zrevrange zs 0 -1
    1) "zzy"
    2) "xiaona"
    3) "xiaotang"
    ################################################
    # count 取一共有几个(1<=count<=3)
    127.0.0.1:6379> zcount zs 1 3
    (integer) 3
    

    事务

    Redis单条命令保证原子性,但事务不保证原子性

    Redis事务没有隔离级别的概念

    Redis的事务:

    • 开启事务 multi
    • 命令入队 ...
    • 执行事务 exec
    127.0.0.1:6379> multi
    OK
    127.0.0.1:6379> set k1 v1
    QUEUED
    127.0.0.1:6379> set k2 v2
    QUEUED
    127.0.0.1:6379> get k2
    QUEUED
    127.0.0.1:6379> exec
    1) OK
    2) OK
    3) "v2"
    

    Redis 实现乐观锁

    ################################################
    #正常执行成功
    127.0.0.1:6379> set money 100
    OK
    127.0.0.1:6379> set out 0
    OK
    127.0.0.1:6379> watch money
    OK
    127.0.0.1:6379> multi
    OK
    127.0.0.1:6379> decrby money 20
    QUEUED
    127.0.0.1:6379> incrby out 20
    QUEUED
    127.0.0.1:6379> exec
    1) (integer) 80
    2) (integer) 20
    ################################################
    # 执行失败 返回nil 多线程修改 
    # 事务执行完注意解锁
    127.0.0.1:6379> watch money out
    OK
    127.0.0.1:6379> multi
    OK
    127.0.0.1:6379> incrby money 20
    QUEUED
    127.0.0.1:6379> decrby money 20
    QUEUED
    127.0.0.1:6379> exec
    (nil)
    127.0.0.1:6379> unwatch
    OK
    

    视频学习资料:B站 狂神说

    https://www.bilibili.com/video/BV1S54y1R7SB?p=1

  • 相关阅读:
    DataAnnotations
    使用BizTalk实现RosettaNet B2B So Easy
    biztalk rosettanet 自定义 pip code
    Debatching(Splitting) XML Message in Orchestration using DefaultPipeline
    Modifying namespace in XML document programmatically
    IIS各个版本中你需要知道的那些事儿
    关于IHttpModule的相关知识总结
    开发设计的一些思想总结
    《ASP.NET SignalR系列》第五课 在MVC中使用SignalR
    《ASP.NET SignalR系列》第四课 SignalR自托管(不用IIS)
  • 原文地址:https://www.cnblogs.com/huacha/p/13991434.html
Copyright © 2011-2022 走看看