【Redis系列1】看完這一篇,Redis就入門了!Redis中9種基本資料型別及常用操作命令和應用場景

2020-10-20 14:00:19

前言

在日常開發中,我們一般都選擇關係型資料庫來儲存資料,如MySQL,Oracle等,但是在並行量比較大的業務場景,關係型資料庫往往會成為系統瓶頸,無法完全滿足我們的需求,所以就誕生了非關係型資料庫,即NoSql資料庫。

NoSql資料庫最常見的解釋是「non-relational」,也有人解釋為「Not Only SQL」。非關係型資料庫不保證事務,也就是不具備ACID特性,這也是非關係型資料庫和關係型資料庫最大的區別,而我們即將介紹的Redis就屬於NoSql資料庫的一種。

PS:本系列文章基於Redis5.0.5版本

為什麼需要NoSql資料庫

相比較於傳統的關係型資料庫,NoSql資料庫具有如下優點:

  • 1、資料之間無關聯關係,非常易於擴充套件
  • 2、支援海量資料的讀寫,高並行下效能更高
  • 3、支援分散式儲存,而且擴縮容簡單

同時,NoSql資料庫的種類也非常多,按照不同的資料儲存型別劃分的話主要有以下常見的NoSql資料庫:

  • 1、key-value儲存。如:Redis和MemcaheDB
  • 2、檔案儲存。如:MongoDB
  • 3、列儲存。如:HBase
  • 4、圖(Graph)儲存。如:Neo4j
  • 5、物件儲存
  • 6、其他型別不再列舉

什麼是Redis

Redis全稱:REmote DIctionary Service,即遠端字典服務。Redis是一個開源的(遵守BSD協定)、支援網路、可基於記憶體亦可持久化的紀錄檔型、Key-Value資料庫。
Redis具有以下特性:

  • 1、支援豐富的資料型別。如字串(strings),雜湊(hashes),列表(lists),集合(sets),有序集合(sorted sets)與範圍查詢, bitmaps等。
  • 2、功能豐富。提供了持久化機制,過期策略,訂閱/釋出等功能
  • 3、高效能,高可用且支援叢集
  • 4、提供了多種語言的API

Redis基本知識介紹

Redis當中採用key和value形式儲存,key和value的最大長度限制是512M。

Redis預設有16個資料庫,這個可以在組態檔redis.conf中做出修改:

databases 16

這16個資料庫以編號0-15命名,不支援修改名字,而且各個資料庫之間的資料並不具備隔離性,比如我們切換到任意一個資料庫,執行命令flushall就可以清空所有資料庫的資料,所以並不建議通過資料庫來隔離不同的業務系統資料,但是我們可以針對同一個業務系統中的不同模組將其設定到不同的資料庫中。

常用資料庫操作命令

  • 切換資料庫。切換資料庫之後會顯示當前所在資料庫編號,預設0號資料庫不顯示編號。
select 資料庫編號

在這裡插入圖片描述
下面圖示可以看到,我們是在0號資料庫設值,所以切換到其他資料庫中無法取到值:
在這裡插入圖片描述

  • 清空當前資料庫
flushdb
  • 清空所有資料庫
flushall

Redis資料型別

Redis中支援的資料型別到5.0.5版本為止,一共有9種。分別是:

  • 1、Binary-safe strings(二進位制安全字串)
  • 2、Lists(列表)
  • 3、Sets(集合)
  • 4、Sorted sets(有序集合)
  • 5、Hashes(雜湊)
  • 6、Bit arrays (or simply bitmaps)(點陣圖)
  • 7、HyperLogLogs
  • 8、 geospatial
  • 9、Streams

雖然這裡列出了9種,但是我們最常用的就是前面5種。

在Redis中,針對每種資料型別都提供了不同的型別的命令,下面就讓我們依次來介紹一下。

1.Binary-safe strings(二進位制安全字串)

字串型別是我們使用最廣泛的一種型別,而且Redis中的key值只能用字串來儲存,而value就可以支援9種資料型別。

Redis當中的字串可以儲存三種資料型別:

  • 字串
  • 整數
  • 浮點數

所以我們字串型別的操作命令還包括了自增命令,下面我們來看一下字串型別的常用操作命令

常用命令

下面介紹幾個常用的操作命令:

  • 設值(只能設值單個key和value)
set key value
  • 設值(多個key和value)
mset key1 value1 key2 value2
  • 取單個值
get key
  • 取多個值
get key1 key2

在這裡插入圖片描述

  • 檢視當前資料庫所有的鍵(這個操作慎用,鍵值過多時可能會直接崩潰)
keys *
  • 檢視當前資料庫鍵的總數(返回一個integer)
dbsize
  • 檢視鍵是否存在當前資料庫(返回的是一個整型:0-否 1-是)
dbsize
  • 重新命名鍵
rename oldKey newKey

在這裡插入圖片描述

  • 刪除鍵(多個以空格隔開,返回的是成功刪除鍵的個數)
del key

在這裡插入圖片描述

  • 檢視鍵的型別
del key

在這裡插入圖片描述

  • 自增1(如果value不是整數,則會報錯)
incr key
  • 自增指定大小(如果value不是整數,則會報錯)
incrby key 需要自增的數位

在這裡插入圖片描述

  • 設值,如果key已經存在則設定失敗
setnx key value # 設定單個key
mset key1 value1 key2 value2 # 設定多個key

在這裡插入圖片描述
PS:setnx和mset是原子操作,必須所有都設定成功才會返回true,其還有引數可以設定過期時間,一般分散式鎖就是基於帶過期時間的這個命令來實現的。

應用場景

字串型別的應用場景非常豐富,正常的熱點資料都可以採用字串型別來進行快取,主要可以應用如下場景:

  • 1、熱點資料及其物件快取
  • 2、分散式Session共用
  • 3、分散式鎖(利用setnx命令)
  • 4、Redis獨立部署,可以用來作為全域性唯一ID
  • 5、利用其原子性遞增命令,可以作為計數器或者限流等

2.Lists(列表)

Redis中的List列表內部的元素也是字串,我們可以將指定元素新增到列表中的指定位置。列表資料型別的操作命令一般都會有小寫字母l開頭。

常用命令

來看一些常用的操作命令:

  • 將一個或者多個value插入到列表key的頭部,key不存在則建立key
lpush key value1 value2
  • 將value插入到列表key的頭部,key不存在則不做任何處理
lpushx key value1 value2
  • 移除並返回key值的列表頭元素
lpop key
  • 將一個或者多個value插入到列表key的尾部,key不存在則建立key
rpush key value1 value2
  • 將一個或者多個value插入到列表key的尾部,key不存在則不做任何處理
rpushx key value
  • 移除並返回key值的列表尾元素
rpop key
  • 返回key列表的長度
llen key
  • 返回key列表中下標為index的元素。頭部從0開始,尾部從-1開始
lindex key index
  • 返回key列表中下標start(含)到stop(含)之間的元素
lrange key start stop
  • 將value設定到key列表中指定index位置。key不存在或者index超出範圍則會報錯
lset key index value
  • 擷取列表中[start,end]之間的元素,並替換原列表儲存
ltrim key start end

在這裡插入圖片描述

3.Sets(集合)

Redis中的集合是一個String型別的無序集合,集合中元素唯一不可重複。

常用命令

Set集合的操作命令一般都以s開頭,下面就列舉一些常用的命令:

  • 將一個或多個元素member加入到集合key當中,並返回新增成功的數目,如果元素已存在則被忽略
sadd key member1 member2
  • 判斷元素member是否存在集合key中
sismember key member
  • 移除集合key中的元素,不存在的元素會被忽略
srem key member1 member2
  • 將元素member從集合source中移動到dest中,如果member不存在,則不執行任何操作
smove source dest member
  • 返回集合key中所有元素
smembers key

在這裡插入圖片描述

4.Sorted Sets(有序集合)

Redis中的有序集合和集合的區別是有序集合中的每個元素都會關聯一個double型別的分數,然後按照分數從小到大的順序進行排列。

常用命令

Sorted Sets集合的操作命令一般都以z開頭,下面就列舉一些常用的命令:

  • 將一個或多個元素member及其score新增到有序集合key中
zadd key score1 member1 score2 member2 
  • 返回有序集合key中member成員的score
zscore key member
  • 將有序集合key中的member加上num ,num可以為負數
zincrby key num member 
  • 返回有序集合key中score值在min(含)到max(含)之間的member數量
zcount key min max
  • 返回有序集合key中score從小到大排列後start(含)到end(含)之間的所有member
zrange key start stop
  • 返回有序集合key中score從大到小排列後start(含)到end(含)之間的所有member
zrevrange key start stop 
  • 返回有序集合中score從min到max的所有元素,按score從小到大排列。注意這裡預設是閉區間,但是可以在max和min前面加上(或者[來控制開閉區間
zrangebyscore key min max
  • 返回有序集合中score從max到min的所有元素,按score從大到小排列。注意這裡預設是閉區間,但是可以在min和max前面加上(或者[來控制開閉區間
zrevrangebyscore key max min
  • 返回有序集合中member中元素排名(從小到大),返回的結果從0開始計算
zrank key member 
  • 返回有序集合中member中元素排名(從大到小),返回的結果從0開始計算
zrevrank key member
  • 返回有序集合中min和max之間的member數量。注意這個命令中的min和max前面必須加(或者[來控制開閉區間,特殊值-和+分別表示負無窮和正無窮
zlexcount key min max

在這裡插入圖片描述

5.Hashes(雜湊)

雜湊表中儲存的是一個key和value的對映表。操作雜湊資料型別的命令一般都是h開頭。

常用命令

下面就是一些常用命令的範例:

  • 將雜湊表key中域field的值設定為value
hset key field value #設定單個field
hmset key field1 value1 field2 value2 #設定多個field
  • 將雜湊表key中域field的值設定為value,如果field已存在,則不執行任何操作
hsetnx key field value
  • 獲取雜湊表key中的域field對應的value
hget key field
  • 獲取雜湊表key中的多個域field對應的value
hmget key field1 field2
  • 刪除雜湊表key中的一個或者多個field
hdel key field1 field2
  • 返回雜湊表key中域的數量
hlen key
  • 為雜湊表key中的域field的值加上增量increment,increment可以為負數,如果field不是數位則會報錯
hincrby key field increment
  • 為雜湊表key中的域field的值加上增量increment,increment可以為負數,如果field不是float型別則會報錯
hincrbyfloat key field increment
  • 為雜湊表key中的域field的值加上增量increment,increment可以為負數,如果field不是數位則會報錯
hincrby key field increment
  • 獲取雜湊表key中的所有域
hkeys key
  • 獲取雜湊表中所有域的值
hvals key

在這裡插入圖片描述

應用場景

雜湊型別和字串型別其實非常像,所以基本上字串能做的事情,雜湊都能做,而且在有些場景下利用雜湊的分類儲存,將會更加高效。

6.Bit arrays (or simply bitmaps)點陣圖

點陣圖bitmap就是通過最小的單位bit來進行0或者1的設定,表示某個元素對應的值或者狀態,其值只能是0或者1,表示是或者否。所以這個一般用於統計是否登入,是否收藏等非否即是的資料。

比如儲存資料格式一般為:100110000111,這裡的0和1就是bit值,設定的時候可以設定指定位置(偏移量)的bit值。

常用命令

點陣圖資料型別主要提供了以下命令:

  • 對key所儲存的字串值,設定或清除指定偏移量offset上的位(bit)值。offset引數必須大於或等於0且小於 2^32 (bit 對映被限制在 512 MB 之內)。
setbit key offset value
  • 獲取指定偏移量offset上的bit值
getbit key offset
  • 計算給定字串中,被設定為1的bit數量,start和end可以省略則統計全部,0表示第1位,-1表示最後一位
bitcount key [start] [end]
  • 返回點陣圖中第一個值為bit的二進位制位的位置,start和end可以省略,0表示第1位,-1表示最後一位
bitpos key bit [start] [end]

在這裡插入圖片描述

應用場景

這個一般應用在非否即是的場景,比如說是否登入,使用者是否留存,是否收藏商品,是否點贊等等。

7.HyperLogLogs

HyperLogLog是Redis 2.8.9 版本新增的一種用來做基數統計演演算法的資料結構。其優點是在輸入元素的數量或者體積非常大時,計算基數所需的空間總是固定的、並且是很小的。這種資料結構一般用於統計UV之類的資訊。

HyperLogLog本身是一種演演算法,其來源於論文《HyperLogLog the analysis of a near-optimal cardinality estimation algorithm》,大家如果對這種演演算法感興趣的可以去了解一下。

在Redis裡面,每個HyperLogLog鍵只需要花費12KB記憶體,就可以計算接近2^64 個不同元素的基數,但是也可能有0.81%的錯誤率。

常用命令

這種資料型別主要提供了以下三個命令:

  • 將任意數量的元素新增到指定的HyperLogLog中的key裡面
pfadd key element1 element2
  • 獲取一個或者多個key的基數
pfcount key1 key2
  • 將多個sourcekey合併到一個destkey中,合併後的destkey中的基數接近於合併前所有sourcekey的並集
pfmerge destkey sourcekey1 sourcekey2

在這裡插入圖片描述
從上面我們可以看到,存進去之後並沒有取出來的命令,所以這個一般就是用來統計,而且需要能接受誤差。

比如上面的範例中,假如u1 u2 u3 u4就是使用者id,那麼我不需要判斷,只要使用者來存取一次網頁我就存一次,最後通過pfcount取出來的值就是去重後的值(也就是上面所說的基數),雖然說有一定誤差,但是像uv這種統計資料是可以接受誤差的。

應用場景

這個一般應用在可以接受誤差場景的資料統計,比如說UV統計等場景

8.geospatial(地理位置)

geospatial是Redis在3.2版本中新增的一種具有半徑查詢的地理空間索引資料型別。一般用來儲存並計算兩地之間的距離。

常用命令

以下就是一些常用命令:

  • 將給定的空間元素(緯度、經度、名字)新增到指定的鍵key裡面。其中有效的經度介於 -180 度至 180 度之間,有效的緯度介於-85.05112878 度至 85.05112878 度之間。
geoadd key longitude latitude member
  • 從鍵key裡面返回所有給定位置元素的位置(經度和緯度)。
geopos key member1 member2
  • 返回兩個給定位置之間的距離。預設單位是米(m),可以通過unit指定,unit支援以下型別:米(m),千米(km),英里(mi),英尺(ft)。
geodist key member1 member2 [unit]
  • 以給定的經緯度為中心,返回鍵包含的位置元素當中,與中心的距離不超過給定最大距離的所有位置元素。
georadius key longitude latitude radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [ASC|DESC] [COUNT count]
  • 以給定的元素為中心,返回鍵包含的位置元素當中,與中心的距離不超過給定最大距離的所有位置元素。
georadiusbymember key member radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [ASC|DESC] [COUNT count]

最後兩個命令基本上是一樣的,一個是需要指定經緯度,一個是會自動讀取某一個元素的經緯度。主要引數含義如下(單位就不重複介紹了):

  • WITHDIST : 在返回位置元素的同時, 將位置元素與中心之間的距離也一併返回。 距離的單位和使用者給定的範圍單位保持一致。
  • WITHCOORD :將位置元素的經度和維度也一併返回。
  • WITHHASH :以52位有符號整數的形式, 返回位置元素經過原始geohash編碼的有序集合分值。這個選項主要用於底層應用或者偵錯, 實際中的作用並不大。
  • ASC:根據中心的位置, 按照從近到遠的方式返回位置元素。
  • DESC:根據中心的位置, 按照從遠到近的方式返回位置元素。
  • COUNT:指定返回的個數。對計算效能影響不大,但是如果返回的區域非常多的情況下,使用count可以節省頻寬

應用場景

這個應用場景就很明顯了,只有需要計算地理位置相關的場景才會需要。

9.Streams

Streams是Redis5.0推出的一種資料型別。支援多播的可持久化訊息佇列,用於實現釋出訂閱功能,Streams的設計借鑑了kafka。Stream是Redis中最複雜的一種資料型別,在這裡我們不展開介紹,後面介紹分佈/訂閱功能的時候再單獨介紹這種資料型別及其強大複雜的操作API。

總結

本文主要介紹了Redis中9種基本資料型別及其常用的操作命令和應用場景進行分析,Redis中的資料型別非常豐富,雖然大部分情況下字串型別就夠用了,但是在某些特定場景使用特定型別將會更加高效和優雅。

下一篇,我們將介紹一下Redis中資料型別底層的資料結構。

請關注我,和孤狼一起學習進步