redis入門指南一書總結下(redis進階)

redis事務

Redis中的事務是一組命令的集合,事務和命令一樣都是Redis的最小執行單位
事務的原理爲:先發送MULTI命令告訴redis接下來將會開啓一個事務,然後發送一系列命令,最後發送執行命令EXEC告訴redis執行這一系列命令。如下就是一個簡單的事務處理:

這裏寫圖片描述

事務通常可以用來保證數據的安全,如果在發送exec命令前客戶端斷線了,那麼redis將會清空事務隊列,事務中的所有命令都不會執行。而一旦客戶端發送了exec命令,即使之後客戶端斷線了也不會影響事務的執行,因爲redis已經記錄了所有要執行的命令
如果事務中的語句發生錯誤,那麼redis將會如何處理呢?首先,我們需要知道是什麼原因導致的錯誤,主要有兩種情況:
1.語法錯誤:命令不存在或者參數的個數不對,只要在事務中存在一個語句出現了語法的錯誤,那麼所有的命令都不會執行,如下:

這裏寫圖片描述

2.運行錯誤:運行錯誤指在命令執行時出現的錯誤,比如使用散列類型的命令操作集合類型的鍵值時,在語法上是沒有錯誤的,然而在運行起來時就會出錯,看如下:

這裏寫圖片描述

這裏需要注意的一點是:redis的事務和大多數的事務不同,它沒有提供rollback回滾操作,想要復原到事務執行之前需要自己進行元素的設置操作來手動實現
有時候對於事務處於安全考慮,我們想要實現這樣一個情況:在事務執行之前如果某個鍵值發生了改變就不執行事務。要實現這樣一個情況就需要使用到另一個強大的命令watch該命令可以監控一個或者多個鍵,一旦在接下來的事務執行之前有一個鍵值發生了改變,那麼事務就不會執行。這裏需要注意的是:這裏所指的事務是接下來的第一個,而不是所有的。看如下:

這裏寫圖片描述

我們發現,最終事務的執行結果爲(nil),也就是redis中的null,因爲在該事物執行之前進行了testkey的修改,所以接下來的事務將不會執行。如果想要取消監視,可以使用命令unwatch,不過該命令只能取消所有的監視,而不能取消指定鍵的監視


生存時間

在實際的開發中經常會遇到一些有時效的數據,比如設計一個限時活動的時候,數據庫中存儲的一些還未使用優惠券等過了優惠的時間就需要刪除這些數據。對於關係數據庫比如MySQL之類的一般需要手動刪除或者額外添加一個字段保存到期時間,然後定期檢測刪除過期數據。而對於redis來說, 這一操作就變得簡單了許多
在redis中,可以使用命令expire來設置一個鍵的生存時間,到指定時間後redis就會自動刪除它,它的命令格式爲:redis> EXPIRE key seconds其中seconds表示鍵的生存時間,單位是秒

這裏寫圖片描述

如果想要設置更精確的生存時間可以通過expireat命令,它的命令格式和expire一樣,只是第二個參數的單位不是秒,而是unix時間戳
想要查看指定鍵當前的剩餘生存時間,可以使用命令ttl

這裏寫圖片描述

在這裏使用命令expire設置鍵值的生存時間時需要注意:我們之前說到的watch命令監視鍵,如果正在被監視的鍵因爲生存時間到期被自動刪除這一修改不會被watch命令認爲該鍵被改變


排序

在前面一篇博客提到redis數據類型時,有一個有序集合類型,它裏面的元素是有序的,而對於其餘的數據類型該如何進行排序呢?
我們可以藉助redis提供的sort命令來對數據進行排序,該命令可以對列表類型、集合類型和有序集合類型進行鍵值排序,其中對有序集合類型的鍵值排序的方式同樣是通過元素自身的值進行排序的,而不是有序集合類型自帶的分數排序

這裏寫圖片描述

sort命令默認只會對數值類型進行排序,如果元素值爲非數值類型,結果就會報錯,因爲redis無法自動將數值類型與字符串類型進行比較,需要我們手動添加參數ALPHA來實現按照字典順序進行排列
redis> SORT key ALPHA
sort命令默認是按照升序進行排列的,我們可以添加DESC參數來實現按照降序進行排列輸出結果
redis> SORT key DESC
sort命令默認是按照元素自身的值進行排序的,如果想要根據其他對應的鍵值進行排序,可以添加by參數,如下圖

這裏寫圖片描述

由上圖可知,我們通過獲取集合set中的每一個元素值,並通過demo.*進行逐個元素值注入並根據demo.*對應的值進行比較然後升序輸出,最終輸出的結果依舊是原來的set集合的值,而不是demo對應的值
sort命令默認是返回集合中的元素的值,如果想要返回指定的鍵值,比如上面的demo對應的值,可以通過get參數來指定,其命令格式和by一樣

這裏寫圖片描述

對於get參數,如果想要返回元素本身的值可以使用#,當然大多數時候是沒有必要的
sort命令默認是直接將結果輸出,如果想要保存結果到指定變量中,可以使用store參數,其後指定一個鍵名或者說字段即可,不管是否存在都行
性能優化:SORT命令是redis最強大也是最複雜的命令之一,該命令的時間複雜度與集合本身元素數量和要返回的元素數量有關,當集合本身元素數量過多或者返回的數量過多時SORT的性能較低,並且redis在使用該命令進行排序前會先建立一個長度爲n(集合本身元素數量)的容器來存儲待排序的元素,雖然是一個臨時過程,但是同時進行的話也會嚴重影響性能


消息通知

前面我們提到過從列表中彈出元素使用的是命令LPOP/RPOP,該命令是非阻塞式命令,如果有元素則彈出並返回該元素的值,如果沒有則輸出(nil),而其實還有一個相對應的比較強大的阻塞時彈出命令:BRPOP
該命令和RPOP命令的唯一區別在於:如果列表中沒有元素則該命令會一直阻塞下去,知道有元素就彈出並返回該元素
我們可以使用該命令來模擬實現一些簡單的消息通知行爲,該命令的格式爲:BRPOP key1 key2 key3,可以同時指定多個列表類型元素,其中如果都沒有元素則會阻塞,從而可以實現任務的優先級:優先執行的任務可以放在前面


發佈/訂閱模式

redis提供了一組命令用於簡單實現redis客戶端之間的通信,對應命令爲:PUBLISH發佈和SUBSCRIBE訂閱,對應的命令格式如下:
//發佈客戶端發佈消息
redis> PUBLISH channer info

//訂閱客戶端接收訂閱消息
redis> SUBSCRIBE channer
其中channer表示訂閱的頻道,它可以看成是一個變量,使用示例看下圖

這裏寫圖片描述

發佈了207 篇原創文章 · 獲贊 75 · 訪問量 36萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章