深入理解redis資料型別

俊俊的小熊餅乾發表於2018-09-28

轉載請註明出處:https://www.cnblogs.com/wenjunwei/p/9720033.html

redis的儲存模型

redis不是普通的鍵值對儲存,它實際上是一個資料結構儲存伺服器,可以支援不同型別的值。這意味著redis相比傳統鍵值對字串key和字串value儲存來說,redis的值可以包含更復雜的資料結構。

redis支援哪些資料結構呢?

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

2.列表(Lists): 根據插入順序排序的字串元素集合。從根本上來說就是連結串列。

3.集合(Sets): 無序且唯一的字串元素集合。

4.有序集合(Sorted sets): 與Sets類似,但每個字串元素都與一個浮點數關聯,稱為分數(score)。這裡的元素總是會按分數來進行排序,因此又與Sets不同。(例如:你可以這樣取值: 我要前十名、我要後十名)

5.雜湊(Hashes): 是由與值相關聯的欄位組成的對映。欄位和值都是字串。這與Ruby或Python雜湊非常相似。

6.位陣列或簡稱點陣圖(Bit arrays or simply bitmaps): 可以使用特殊命令處理字串值,如:您可以設定和清除各個位,將所有位設定為1,查詢第一組或未設定位等等。

7.HyperLogLogs: 這是一個概率資料結構,用於計算集合的基數。

 

Redis Key

RedisKey是二進位制安全的,這意味著您可以使用任何二進位制序列作為key,從”foo”這樣的字串到JPEG檔案內容,又或者是空字串,都是有效鍵。

rediskey的一些規則:

1.key太長是不好的。例如:一個1024位元組的key,在記憶體方面就佔用不少,而且在資料集中查詢key的時候可能會需要幾次高昂的key對比的過程。即使現在任務需要一個很大的key,我們通過雜湊法hashing(如SHA1)來獲得key,從頻寬和記憶體來看,這也是一個更好的辦法。

2.key太短也是不好的。如果你將一個”user:1000:followers”的key改為”u1000flw”,那是沒有任何意義的。因為這種做法節省的空間很小,但是前者會更顧名思義。我們在工作中應該要找到一個衡量key值的平衡點。

3.最好堅持使用一種命名格式。例如:“object-type:id”,如“user:1000”。而點或短劃線通常用於多字詞欄位,如“comment:1234:reply.to”或“comment:1234:reply-to”。可以定一個命名規範。

4.最大記憶體。redis中允許的key值最大是512MB。

 

Redis expires:有時間限制的key

在使用更復雜的資料結構之前,我們討論一個無論任何資料型別都有的一個特性,稱為Redis過期。您可以為key設定一個超時時間,這是一個有限的生存時間。當生存時間過去時,key就會自動銷燬,就類似於key被呼叫了del命令一樣。

關於redis到期資訊:

1.可以使用秒或者毫秒精度進行設定。

2.但是,到期時間的分辨係數始終為1毫秒。

3.過期資訊將被複制保留在磁碟中,當redis伺服器停止時,時間依然在度過(這意味著redis會儲存key過期的時間)。

 

一.Redis String

Redis的String型別是最簡單的型別,與redis key有著密切關聯。也是Memcached中唯一的資料型別,對於新手來說,在redis使用這個型別是很自然的。

由於Redis key是字串,當value也是字串的時候,會將字串對映到另一個字串。

常見例項:

1.例如快取HTML片段或頁面。

2.session快取。

3.驗證碼快取。

  

二.Redis Lists

列表實現主要有陣列和連結串列,兩種實現方法的到的list的屬性差異很大。Redis Lists是通過連結串列實現的。這意味著即使列表中有數百萬個元素,在列表頭部或尾部新增元素的速度都是一樣的。當然連結串列結構也是有缺點的,使用陣列實現list,通過索引訪問元素的速度非常快,而使用連結串列就咩有那麼快了。

Redis使用連結串列實現Lists,對於資料庫而言,最重要的是能夠以非常快的方式將元素新增到很長的列表中。當快速訪問大量元素集合的中間位置很重要時,可以使用不同的資料結構,稱為sorted sets(後面會介紹到)。

常見例項

1.記住使用者釋出到社交網路的最新訊息。

2.流程之間的通訊,使用生產者將專案列表推入訂閱模式。redis具有特殊的命令,使用這些用例更加的可靠和高效。

3.每次使用者釋出新照片,我們都可以將其ID新增到列表中。

4.當使用者訪問主頁時,我們通過LRANGE 0 9命令獲取最新的10個專案。

 

三.Redis Hashes

我們可以將Redis Hashes看為使用`雜湊`作為對key/value的對映表。

新增和刪除操作都是O(1)(平均)的複雜度。hash型別特別適合用於儲存物件,但是放入的hash物件實際上的沒有限制(除了可用記憶體之外),因此在應用程式中可以以許多不同的方式使用雜湊。

在field的數量在限制的範圍內以及value的長度小於指定的位元組數,即小雜湊中,會在記憶體中以特殊的方式編碼,會比較節省記憶體。

常用例項:

1.用於儲存關係資料表或物件資訊:如 {name:`張三`,age:17}

四.Redis Sets

Redis Sets是無序的字串集合。我們可以用作元素集合儲存,也可以針對集合做其他操作。比如測試給定的元素是否存在,執行多個集合之間的交集,並集或差異等。

儲存的資料結構是雜湊表,所以增刪改查的操作複雜度都是O(1)。

常見例項:

1.用於集合去重。

2.用於分散式鎖。

 

五.Redis Sorted Sets

Sorted Sets資料型別就像是set和hash的混合。與sets一樣,Sorted Sets是唯一的,不重複的字串組成。可以說Sorted Sets也是Sets的一種。

雖然在Sets內部元素沒有進行排序,但是Sorted Sets中每個元素都與浮點值相關聯,稱為分數(因為每個元素都對映到一個值,所以說有點類似hash)。

此外,Sorted Sets中的元素按順序排序,他們的規則如下:

1.如果A和B是兩個具有不同分數的元素,如果A.score > B.score,則 A > B。

2.如果A和B分數相同,如果A字串在字典排序上大於B字串,則A>B。在Sorted Sets中A、B字串不能相等。

實現方式:Sorted Sets是通過Skip List(跳躍表)和hash Table(雜湊表)的雙埠資料結構實現的,因此每次新增元素時,Redis都會執行O(log(N))操作。所以當我們要求排序的時候,Redis根本不需要做任何工作了,早已經全部排好序了。元素的分數可以隨時更新。

常見例項:

1.獲取排行集合:獲取第10-50名元素集合。

2.在分數範圍操作:獲取分數在60-80的元素集合。

3.Redis2.8後,在分數相同情況下,我們還可以根據字典順序進行排序。

4.可以獲取某個元素在集合中的名次。

 

六.Bitmaps

點陣圖不是實際的資料型別,而是String型別上定義了一組面向位的操作。由於字串是二進位制安全的blob ,並且他們的最大長度為512MB,所以他們最多適合2^32不同的位。

點陣圖的最大優勢之一就是他們在儲存資訊時通常可以節省大量的空間。

常見例項:

1.各種實時分析。

2.儲存與物件ID關聯的節省空間但高效能的布林資訊。

 

七.HyperLogLogs

HyperLogLogs是用來做基數(不重複元素)統計的演算法。HyperLogLog 的優點是,在輸入元素的數量或者體積非常非常大時,計算基數所需的空間總是固定 的、並且是很小的。

在 Redis 裡面,每個 HyperLogLog 鍵只需要花費 12 KB 記憶體,就可以計算接近 2^64 個不同元素的基 數。這和計算基數時,元素越多耗費記憶體就越多的集合形成鮮明對比。

但是,因為 HyperLogLog 只會根據輸入元素來計算基數,而不會儲存輸入元素本身,所以 HyperLogLog 不能像集合那樣,返回輸入的各個元素。

常見例項:

1.用來做基數統計的演算法

 

 總結

通過上面的型別介紹,我們使用Redis時,通常會接觸Redis的5種物件型別(字串、雜湊、列表、集合、有序集合),而每一種資料型別都有著各自的特性,我們需要根據自己的應用場景選擇最合適的資料型別,利用最合適的特性,可以達到事半功倍的效果。

 

感謝您的閱讀,如果您覺得閱讀本文對您有幫助,請點一下“推薦”按鈕。本文歡迎各位轉載,但是轉載文章之後必須在文章頁面中給出作者和原文連線。

相關文章