本篇內(nèi)容主要講解“常見redis數(shù)據(jù)結(jié)構(gòu)有哪些”,感興趣的朋友不妨來(lái)看看。本文介紹的方法操作簡(jiǎn)單快捷,實(shí)用性強(qiáng)。下面就讓小編來(lái)帶大家學(xué)習(xí)“常見Redis數(shù)據(jù)結(jié)構(gòu)有哪些”吧!
十多年的且末網(wǎng)站建設(shè)經(jīng)驗(yàn),針對(duì)設(shè)計(jì)、前端、開發(fā)、售后、文案、推廣等六對(duì)一服務(wù),響應(yīng)快,48小時(shí)及時(shí)工作處理。成都營(yíng)銷網(wǎng)站建設(shè)的優(yōu)勢(shì)是能夠根據(jù)用戶設(shè)備顯示端的尺寸不同,自動(dòng)調(diào)整且末建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無(wú)論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設(shè)計(jì),從而大程度地提升瀏覽體驗(yàn)。成都創(chuàng)新互聯(lián)公司從事“且末網(wǎng)站設(shè)計(jì)”,“且末網(wǎng)站推廣”以來(lái),每個(gè)客戶項(xiàng)目都認(rèn)真落實(shí)執(zhí)行。
有Java基礎(chǔ)的應(yīng)該知道常用的一些數(shù)據(jù)結(jié)構(gòu),比如數(shù)組、隊(duì)列、棧等等... 那Redis的數(shù)據(jù)結(jié)構(gòu)跟Java的數(shù)據(jù)結(jié)構(gòu)有什么區(qū)別嗎?答案是有的,如果一些小伙伴了解的Map的話就知道Map中有一個(gè)Key值和一個(gè)Value值,Redis的數(shù)據(jù)結(jié)構(gòu)也是這樣的。
Redis的數(shù)據(jù)結(jié)構(gòu):String、List、Hash、Set的話都是有一個(gè)Key值和一個(gè)Value值。
Key值是名字,Value值就是數(shù)據(jù)。這兩個(gè)是綁定在一起的,一個(gè)Key值對(duì)應(yīng)一個(gè)Value值,我們稱之這樣的為鍵值對(duì)。
在Redis中,在不同的場(chǎng)景下會(huì)使用不同的命令。但是不是每個(gè)命令都需要記住呢?不是的,只需要熟悉最常用的命令就好了,在需要使用一些少用的命令可以去官方文檔查閱即可。下面來(lái)介紹Redis中一些常用的命令。
1.# exists(判斷key值是否存在):如果存在返回1,反之返回0 例子: exists name(name為key) 2.# del(刪除key): 刪除成功返回1,反之返回0 3.# type(判斷key的類型) 4.ttl(查看key存活時(shí)間
想學(xué)習(xí)更多命令可以自行到中文文檔進(jìn)行查詢:http://www.redis.cn/
String字符串類型是Redis中最基本的數(shù)據(jù)類型,在Redis中的應(yīng)用場(chǎng)景很廣,一個(gè)key對(duì)應(yīng)一個(gè)value。
Redis的String是動(dòng)態(tài)字符串,可修改的字符串,它的內(nèi)部結(jié)構(gòu)類似于Java的ArrayList,采用預(yù)分配冗余空間的方式來(lái)減少內(nèi)存的分配。
String類型是二進(jìn)制安全的,意思就是Redis的String可以包含任何的數(shù)據(jù)。如:數(shù)字,字符串,圖片等
String類型的應(yīng)用場(chǎng)景:驗(yàn)證碼、計(jì)數(shù)器、訂單重復(fù)提交、用戶登錄信息、商品詳情的實(shí)現(xiàn)
1.# set/get 設(shè)置和獲取key-value 注意中間一定要加空格 例子: set xxx(key) xxx(value) get xxx(key) 2.# mget/mset 批量設(shè)置或獲取多個(gè)key的值 mset user:name jack user:age 2 mget user:name user:age 3.# incr incr對(duì)key對(duì)應(yīng)的值進(jìn)行加1操作,并返回新的值 incr video:uv:1 4. # incrby 將key對(duì)應(yīng)的數(shù)字加increment.如果key不存在,操作之前,key就會(huì)被置為0 incrby video:uv:1 10 5.# setex 設(shè)置key對(duì)應(yīng)字符串value,并且設(shè)置key在給定的seconds時(shí)間之后超時(shí)過(guò)期操作 setex code 20 778899 (設(shè)置一個(gè)key為code value為778899 20秒后過(guò)期)4 6. # setnx 將key設(shè)置值為value,如果存在該key那么什么都不做,如果不存在key那么等同于set命令 setnx name xdclass.net 7. # getset 設(shè)置key的值,并返回key舊的值 get name uuuuu (這時(shí)會(huì)返回xdclass.net,重新在get一下會(huì)獲得重新設(shè)置的值uuuuu)
注意:值的長(zhǎng)度不能超過(guò)512MB,遵循key的命名規(guī)范:業(yè)務(wù)名:表明:ID(不要過(guò)長(zhǎng),用冒號(hào)分割)
Redis中沒有使用C語(yǔ)言的傳統(tǒng)字符串來(lái)表示,而是構(gòu)建了一種名為簡(jiǎn)單動(dòng)態(tài)字符串(SDS)的抽象類型。為什么Redis要用自己構(gòu)建的SDS而不是直接用C語(yǔ)言的String呢?原因其實(shí)很簡(jiǎn)單,就是為了提升Redis操作的性能。
常數(shù)復(fù)雜度獲取字符串長(zhǎng)度:C語(yǔ)言想獲取長(zhǎng)度,那么它必須要遍歷一整個(gè)字符串才行。SDS通過(guò)len屬性獲取SDS字符串長(zhǎng)度的時(shí)間復(fù)雜度從O(N)變成了O(1),保證了獲取字符串長(zhǎng)度時(shí)不會(huì)成為Redis的性能瓶頸。
減少修改帶來(lái)的內(nèi)存重新分配次數(shù):內(nèi)存重分配就是說(shuō)在修改字符串時(shí),由于內(nèi)存空間的不足或者是超出了,需要對(duì)執(zhí)行內(nèi)存的重分配操作,這種操作由于會(huì)涉及到內(nèi)存,所以導(dǎo)致時(shí)間的成本高,所以我們應(yīng)該盡量的避免內(nèi)存重分配。而在SDS就是有l(wèi)en和free這兩個(gè)屬性,可以使用優(yōu)化策略來(lái)減少對(duì)內(nèi)存重分配次數(shù)。
List類型說(shuō)白了就是一個(gè)鏈表 ,插入元素進(jìn)去后是有序排列的,value值是可以重復(fù)的,可以通過(guò)對(duì)應(yīng)的下標(biāo)獲取對(duì)應(yīng)的value值,鏈表的左右兩邊都能進(jìn)行插入和刪除數(shù)據(jù)。在插入時(shí),如果該鍵并不存在,那么Redis將為該鍵創(chuàng)建一個(gè)新的鏈表。與此相反,如果這個(gè)鏈表中的所有元素都被刪除,那么該鍵也會(huì)被刪除掉。
應(yīng)用場(chǎng)景:簡(jiǎn)單隊(duì)列、最新評(píng)論列表、非實(shí)時(shí)排行榜:定時(shí)計(jì)算榜單,如手機(jī)日銷榜單
1. # lpush 將一個(gè)或多個(gè)值插入到列表頭部 lpush phone:rank:daily iphone6 2. # rpop 移除并獲取列表的最后一個(gè)元素 rpor phone:rank:daily 3. # llen 獲取列表長(zhǎng)度 llen phone:rank:daily 4. # lrange 獲取key對(duì)應(yīng)的list的指定下標(biāo)范圍元素,其中0表示列表的第一個(gè)元素,-1表示獲取列表的所有元素 lrange phone:rank:daily 0 -1 5. # rpush 在key對(duì)應(yīng)的list尾部添加一個(gè)元素 rpush phone:rank:daily xiaodi 6. # lpop 從key對(duì)應(yīng)的List的尾部刪除一個(gè)元素,并返回該元素 lpop phone:rank:daily 7. # bropo 移出并獲取列表的最后一個(gè)元素,如果列表沒有元素會(huì)阻塞列表直到等待超時(shí)或發(fā)現(xiàn)可彈出元素為止 brpop phone:rank:daily 20 8. # lrem 移除元素 lrem phone:rank:daily 2 a
上面了解了List的常用命令的使用,我們現(xiàn)在就來(lái)看下list的底層結(jié)構(gòu)。
List有兩種實(shí)現(xiàn)方式
壓縮鏈表(ziplist):是Redis為了節(jié)省內(nèi)存空間而開發(fā)的,它是特殊編碼的連續(xù)內(nèi)存塊而組成的一個(gè)順序數(shù)據(jù)結(jié)構(gòu),一個(gè)壓縮列表 可以包含許多任意的節(jié)點(diǎn),它的重點(diǎn)是內(nèi)存連續(xù)!
雙端鏈表:使用prev和next這兩個(gè)指針,是可以從前向后也可以從后向前來(lái)實(shí)現(xiàn)lpush和rpush這些指令。因?yàn)槭擎湵?,所以也?dǎo)致了lindex指令獲取某個(gè)元素需要遍歷鏈表才能獲取得到。時(shí)間復(fù)雜度O(n)。
當(dāng)列表的對(duì)象同時(shí)滿足下述兩個(gè)條件時(shí),列表對(duì)象采用壓縮鏈表編碼:
(1)列表對(duì)象保存的所有元素長(zhǎng)度都小于64個(gè)字節(jié);
(2)列表元素所保存的元素個(gè)數(shù)小于512個(gè)
在Redis3.2之后,采用的是快速鏈表-quicklist。quicklist是一個(gè)雙向鏈表,并且它還是一個(gè)有ziplist特性的雙向鏈表,就是說(shuō)quicklist每個(gè)節(jié)點(diǎn)都是ziplist。這個(gè)快速鏈表結(jié)合了兩者的優(yōu)點(diǎn)。
Redis中的Hash類型是一個(gè)String類型的field和value的映射表,Hash特別適合用于存儲(chǔ)對(duì)象,Hash類似于Map結(jié)構(gòu)。因?yàn)樵赗edis里,Hash又是另外的一種鍵值對(duì)結(jié)構(gòu),而Redis本身就是key-value類型,所以這個(gè)Hash結(jié)構(gòu)是套在了Redis下的value里。
下面說(shuō)說(shuō)Hash的底層數(shù)據(jù)結(jié)構(gòu):
一種是ziplist ,當(dāng)存儲(chǔ)的數(shù)據(jù)超過(guò)所配置的數(shù)量大小時(shí)就是轉(zhuǎn)成Hashtable這種結(jié)構(gòu)。這種轉(zhuǎn)換會(huì)比較消耗性能,所以盡量少用這種轉(zhuǎn)換操作。
另一種就是hashtable ,這種結(jié)構(gòu)的時(shí)間復(fù)雜度為O(1),但是會(huì)比較消耗內(nèi)存空間。
對(duì)于Hash在Redis中的應(yīng)用場(chǎng)景:購(gòu)物車、用戶個(gè)人信息、商品詳情的實(shí)現(xiàn)
1. # hset 設(shè)置key指定的哈希集指定字段的值 hset product:detail:1 title iphone11 2. # hget 返回key指定的哈希集中該字段所關(guān)聯(lián)的值 hget product:detail:1 title 3. # hgetall 返回key指定的哈希集中所有的字段和值 hegetall product:detail:1 4. # hdel 從key指定的哈希集中移除指定的域 hdel product:detail:1 title 5. # hexists 返回hash里面的field是否存在 hexists product:detail:1 title (存在返回1,不存在返回0) 6. # hincrby 增加key指定的哈希集中的指定字段的數(shù)值,如果是-1則是遞減 hincrby product:detail:1 key 1 (對(duì)key里的value值進(jìn)行遞增或遞減) 7. # hmset 設(shè)置key指定的哈希集中指定字段的值 hmset product:detail:2 title xiaomi price 1000 stock 10 8. # hmget 返回key指定的哈希集中指定字段的值 hmget product:detail:2 title price
注意:每個(gè)Hash可以存儲(chǔ)232-1鍵值對(duì)
Redis中的Set類型是一個(gè)集合,集合的概念是一堆不重復(fù)的組合。利用Redis提供的Set數(shù)據(jù)結(jié)構(gòu)可以存儲(chǔ)一些集合性的數(shù)據(jù)。因?yàn)镽edis很友好的為集合提供了求集、并集、差集等操作( PS:不懂的同學(xué)可以問下以前的數(shù)學(xué)老師哦~哈哈哈哈),那么就可以非常方便的實(shí)現(xiàn)共同關(guān)注、共同喜好等功能。對(duì)上面的集合操作,你還可以使用不同的命令選擇獎(jiǎng)結(jié)果返回給客戶端還是存集合到一個(gè)新的集合中。
Redis中Set應(yīng)用場(chǎng)景:去重、社交應(yīng)用關(guān)注(粉絲,共同好友)、統(tǒng)計(jì)網(wǎng)站PV(UV、IP)大數(shù)據(jù)里面的用戶畫像標(biāo)簽集合
1. # sadd 添加一個(gè)或多個(gè)指定的元素到集合中,如果指定的元素已經(jīng)在集合key中則忽略 sadd user:tags female sadd user:tags bmw 2. # scard 返回集合存儲(chǔ)的key的基數(shù)(集合元素的數(shù)量) scard user:tags 3. # sdiff 返回的集合元素是第一個(gè)key集合與后面所有key集合的差集 sdiff user:tags:1 user:tags:2 4. # sinter 返回指定所有的集合的成員的交集 sinter user:tags:1 user:tags:2 5. # sismember 返回成員是否有存儲(chǔ)的集合key的成員 sismember user:tags:1 bmw 6. # srem 在集合中移除指定的元素,如果指定元素不是key集合中的則忽略 srem user:tags:1 bmw 7. # sunion 返回給定的多個(gè)集合的并集所有的成員 sunion user:tags:1 user:tags:2
和Set相比,SortedSet是將Set中的元素增加了一個(gè)權(quán)重參數(shù)score,使得集合中的元素能夠按 score進(jìn)行有序排序,比如存儲(chǔ)一個(gè)存儲(chǔ)班上同學(xué)成績(jī)的SortedSet集合,該集合value可以設(shè)為同學(xué)的學(xué)號(hào),然而score就可以是考試成績(jī)。這樣才插入數(shù)據(jù)的時(shí)候,就已經(jīng)為數(shù)據(jù)進(jìn)行了排序。另外,SortedSet還可以用來(lái)做帶權(quán)重的隊(duì)列。
應(yīng)用場(chǎng)景:實(shí)時(shí)排行榜、優(yōu)先級(jí)任務(wù)(隊(duì)列)、朋友圈(文章)點(diǎn)贊-取消
跳躍表實(shí)則是一個(gè)鏈表,在傳統(tǒng)的鏈表中想要查找一個(gè)元素就要從最原始的地方開始查找,直到查找到該元素。在跳躍表中呢,它會(huì)把鏈表進(jìn)行抽層,抽層的時(shí)候會(huì)隔幾個(gè)元素分為一個(gè)節(jié)點(diǎn),抽層之后也是一條鏈表,節(jié)點(diǎn)會(huì)變少了。如下圖所示,當(dāng)要尋找元素78時(shí),如果是尋常的鏈表就會(huì)從左往右挨個(gè)查詢,這時(shí)查詢了8次才能找?guī)г撛?。?dāng)使用跳躍表后,從第二層的開始出發(fā),當(dāng)查詢到79這個(gè)節(jié)點(diǎn)時(shí)發(fā)現(xiàn)沒有78,則返回到57這個(gè)節(jié)點(diǎn)再返回第一層去尋找該元素。
1.# zadd 向有序集合里添加一個(gè)或者多個(gè)成員,或者更新已存在成員的分?jǐn)?shù) zadd video:rank 90 springcloud zadd video:rank 80 springboot zadd video:rank 50 redis 2.# zcard 獲取有序集合的成員數(shù) zcard video:rank 3.# zcount 計(jì)算在有序集合中指定的區(qū)間分?jǐn)?shù)的成員數(shù) zcount video:rank 0 60 4.# zincrby 在有序集合中對(duì)指定成員的分?jǐn)?shù)加上增量 zincrby video:rank 2 springcloud 5.# zrange 通過(guò)索引區(qū)間返回有序集合指定內(nèi)的成員,成員位置分?jǐn)?shù)按(從小到大排序) zrange voideo:rank 0 -1 zrange voideo:rank 0 -1 withscores(返回分?jǐn)?shù)) 6.# zrevrange 通過(guò)索引集合中指定成員的排名,其中有序集合成員按score值遞增(從大到小排序) zrevrange voideo:rank 0 -1 7.# zrevrank 返回有序集合中指定的成員排名,有序集合成員按分?jǐn)?shù)遞減(從大到小排序) zrevrank voideo:rank springcloud 8.# zrank 返回有序集key中成員member的排名,其中有序集成員按score值遞增(從小到大排序) zrank voideo:rank 9.# zrem 移除有序集合中的一個(gè)或者多個(gè)成員 zrem voideo:rank redis 10.# zscore 返回有序集合中的成員分?jǐn)?shù)值 zscore voideo:rank springcloud
到此,相信大家對(duì)“常見Redis數(shù)據(jù)結(jié)構(gòu)有哪些”有了更深的了解,不妨來(lái)實(shí)際操作一番吧!這里是創(chuàng)新互聯(lián)網(wǎng)站,更多相關(guān)內(nèi)容可以進(jìn)入相關(guān)頻道進(jìn)行查詢,關(guān)注我們,繼續(xù)學(xué)習(xí)!
網(wǎng)站標(biāo)題:常見Redis數(shù)據(jù)結(jié)構(gòu)有哪些
轉(zhuǎn)載來(lái)源:http://bm7419.com/article40/goseho.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供定制開發(fā)、App設(shè)計(jì)、全網(wǎng)營(yíng)銷推廣、動(dòng)態(tài)網(wǎng)站、虛擬主機(jī)、品牌網(wǎng)站建設(shè)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)