真实的国产乱ⅩXXX66竹夫人,五月香六月婷婷激情综合,亚洲日本VA一区二区三区,亚洲精品一区二区三区麻豆

成都創(chuàng)新互聯(lián)網(wǎng)站制作重慶分公司

Redis數(shù)據(jù)結構中的String類型有哪些

這篇文章主要介紹“redis數(shù)據(jù)結構中的String類型有哪些”,在日常操作中,相信很多人在Redis數(shù)據(jù)結構中的String類型有哪些問題上存在疑惑,小編查閱了各式資料,整理出簡單好用的操作方法,希望對大家解答”Redis數(shù)據(jù)結構中的String類型有哪些”的疑惑有所幫助!接下來,請跟著小編一起來學習吧!

創(chuàng)新互聯(lián)公司2013年至今,先為永清等服務建站,永清等地企業(yè),進行企業(yè)商務咨詢服務。為永清企業(yè)網(wǎng)站制作PC+手機+微官網(wǎng)三網(wǎng)同步一站式服務解決您的所有建站問題。

Redis數(shù)據(jù)結構中的String類型有哪些

Redis常用作分布式KV緩存,很多人僅僅只會使用,卻不知道底層卻有著很多不為人知的秘密。

String類型

String作為Redis支持的最基礎的數(shù)據(jù)類型,首先我們來看下String,他的數(shù)據(jù)結構和存儲是怎么樣的。

重新定義SDS 去存儲String

眾所周知,redis是用c語言進行編寫的,而c語言是沒有String類型的,只有char[],并且在初始化的是時候就必須大小指定類型后就不能改變。為了實現(xiàn)動態(tài)增加和擴展等功能,如incr命令,append命令,所以redis就自己定義維護了一個SDS(Simple Dynamic String)來實現(xiàn)這些功能。

我們先來看一下redis源碼中定義的數(shù)據(jù)結構,這里有5種類型,目的是為了節(jié)省空間。

Redis數(shù)據(jù)結構中的String類型有哪些

1、len:獲取char[]的長度,需要遍歷數(shù)組,len(char[])時間復雜度O(n);
2、alloc:c語言沒有String類型, 只有char[],且char[]必須先分配空間長度,char[]預先分配了長度,數(shù)據(jù)增長后需要擴容;

3、falgs:總是占用一個字節(jié)。其中的最低3個bit用來表示header的類型。header的類型共有5種,在sds.h中有常量定義。
4、buf[]:c語言的char數(shù)組,用'\0'代表結束,意味著存儲二進制數(shù)據(jù)不能包含'\0',圖片音頻等用二進制存儲會有問題——這就是為什么Redis說自己實現(xiàn)的SDS是二進制安全的字符串。

SDS對c原始char數(shù)組的改進

1、Redis實現(xiàn)的SDS支持擴容
2、包含長度len,獲取長度復雜度O(1)
3、空間預分配
4、惰性空間釋放(下面會講)

SDS的優(yōu)缺點

優(yōu)點

  • 能夠支持擴容

  • 包含長度len,獲取長度復雜度O(1)

  • 空間預分配

缺點

  • 需要分配額外的內存

  • 頻繁的分配和回收帶來的效率問題

Redis 使用的內存分配庫 jemalloc

jemalloc 在分配內存時,會根據(jù)我們申請的字節(jié)數(shù) N,找一個比 N 大,但是最接近 N 的 2 的冪次數(shù)作為分配的空間,這樣可以減少頻繁分配的次數(shù)。舉個例子。如果你申請 6 字節(jié)空間,jemalloc 實際會分配 8 字節(jié)空間;如果你申請 24 字節(jié)空間,jemalloc 則會分配 32 字節(jié)。所以,在我們剛剛說的場景里,dictEntry 結構就占用了 32 字節(jié)。

空間預分配

空間預分配用于優(yōu)化 SDS 的字符串增長操作: 當 SDS 的 API 對一個 SDS 進行修改, 并且需要對 SDS 進行空間擴展的時候, 程序不僅會為 SDS 分配修改所必須要的空間, 還會為 SDS 分配額外的未使用空間。

其中, 額外分配的未使用空間數(shù)量由以下公式?jīng)Q定:

  • 如果對 SDS 進行修改之后, SDS 的長度(也即是 len 屬性的值)將小于 1 MB , 那么程序分配和 len 屬性同樣大小的未使用空間, 這時 SDS len 屬性的值將和 free 屬性的值相同。 舉個例子, 如果進行修改之后, SDS 的 len 將變成 13 字節(jié), 那么程序也會分配13 字節(jié)的未使用空間, SDS 的 buf 數(shù)組的實際長度將變成 13 + 13 + 1 = 27 字節(jié)(額外的一字節(jié)用于保存空字符)。

  • 如果對 SDS 進行修改之后, SDS 的長度將大于等于 1 MB , 那么程序會分配 1 MB 的未使用空間。 舉個例子, 如果進行修改之后, SDS 的 len 將變成 30 MB , 那么程序會分配 1 MB 的未使用空間, SDS 的 buf 數(shù)組的實際長度將為 30 MB + 1 MB + 1 byte 。

通過空間預分配策略, Redis 可以減少連續(xù)執(zhí)行字符串增長操作所需的內存重分配次數(shù)。

惰性釋放

惰性空間釋放用于優(yōu)化 SDS 的字符串縮短操作: 當 SDS 的 API 需要縮短 SDS 保存的字符串時, 程序并不立即使用內存重分配來回收縮短后多出來的字節(jié), 而是使用 free 屬性將這些字節(jié)的數(shù)量記錄起來, 并等待將來使用。

Redis的KV存儲結構

在redis中,所有的存儲都是以KV鍵值對的形式存儲的,K是字符串類型,就是SDS;V 可能是字符串、list、hash等(Redis支持的數(shù)據(jù)結構),V并沒有直接定成具體的類型,而是用redisObject封裝了一層;實際存儲的數(shù)據(jù)結構是由ptr指針具體指向。

并且,redis為了更好的節(jié)省空間,ptr指針也有不同方式的存儲,一方面,當保存的是 Long 類型整數(shù)時,RedisObject 中的指針就直接賦值為整數(shù)數(shù)據(jù)了,這樣就不用額外的指針再指向整數(shù)了,節(jié)省了指針的空間開銷。另一方面,當保存的是字符串數(shù)據(jù),并且字符串小于等于 44 字節(jié)時,RedisObject 中的元數(shù)據(jù)、指針和 SDS 是一塊連續(xù)的內存區(qū)域,這樣就可以避免內存碎片。這種布局方式也被稱為 embstr 編碼方式。當然,當字符串大于 44 字節(jié)時,SDS 的數(shù)據(jù)量就開始變多了,Redis 就不再把 SDS 和 RedisObject 布局在一起了,而是會給 SDS 分配獨立的空間,并用指針指向 SDS 結構。這種布局方式被稱為 raw 編碼模式。如圖所示

Redis數(shù)據(jù)結構中的String類型有哪些

  • embstr 編碼
    存儲簡短字符串,一次的內存分配;
    它是只讀的,如果對內容進行修改,就會變成raw編碼(即使沒超過44字節(jié));

  • raw 編碼
    可分配多次內存空間,存儲大于44個字節(jié)的長字符串。

raw 原生SDS 字符長度 縮減到小于44,會逆向變成embstr編碼嗎?
不會;Redis底層編碼,轉變后 不可逆(不會回退)。

到此,關于“Redis數(shù)據(jù)結構中的String類型有哪些”的學習就結束了,希望能夠解決大家的疑惑。理論與實踐的搭配能更好的幫助大家學習,快去試試吧!若想繼續(xù)學習更多相關知識,請繼續(xù)關注創(chuàng)新互聯(lián)網(wǎng)站,小編會繼續(xù)努力為大家?guī)砀鄬嵱玫奈恼拢?/p>
當前文章:Redis數(shù)據(jù)結構中的String類型有哪些
轉載注明:http://weahome.cn/article/pscggc.html

其他資訊

在線咨詢

微信咨詢

電話咨詢

028-86922220(工作日)

18980820575(7×24)

提交需求

返回頂部