天天看點

高可用Redis(二):字元串類型

1.Redis字元串結構

對于Redis來說,所有的key都是字元串,其value可以是string,list,hash,set,zset

比如下面的

高可用Redis(二):字元串類型

鍵值對的value還可以更加複雜,比如可以是json格式,xml格式,序列化等

字元串類型的value的長度不能大于512MB。

在實際生産中,如果一個值儲存成500MB的話,擷取這個值的時候會占用很多的網絡流量,其次讀取的時候也會非常慢,這對于Redis這種單線程應用來說并不明智

在生産環境中,考慮到并發和網絡流量的因素,value的大小建議在100KB以内

Redis字元串的使用場景:

緩存
計數器,比如視訊網站中視訊的播放次數統計等
分布式鎖           

2.Redis字元串相關指令

2.1 get指令,set指令和del指令

get key             擷取key對應的value
set key value       設定key-value
del key             删除key-value           

例子:

127.0.0.1:6379> set hello 'world'
OK
127.0.0.1:6379> get hello
"world"
127.0.0.1:6379> del hello
(integer) 1
127.0.0.1:6379> get hello
(nil)           

注意事項:

get指令,set指令和del指令的時間複雜度都是O(1)           

2.2 整型操作指令

incr key        key自增1,如果key不存在,自增後get(key) = 1
decr key        key自減1,如果key不存在,自減後get(key) = -1
incrby key k    key自增k,如果key不存在,自增後get(key) = k
decrby key k    key自減k,如果key不存在,自減後get(key) = -k           
127.0.0.1:6379> get counter
(nil)
127.0.0.1:6379> incr counter
(integer) 1
127.0.0.1:6379> get counter
"1"
127.0.0.1:6379> incrby counter 99
(integer) 100
127.0.0.1:6379> get counter
"100"
127.0.0.1:6379> decr counter
(integer) 99
127.0.0.1:6379> get counter
"99"
127.0.0.1:6379> decrby counter 50
(integer) 49
127.0.0.1:6379> get counter
"49"           
incr/decr指令和incrby/decrby指令時間複雜度為O(1)
Redis是天然适合做計數器的
Redis是單線程的,順序執行,并發執行incr指令不會有競争的問題,不會計錯數           

實戰

記錄網站每個使用者的個人首頁的通路量,可以使用如下指令

incr userid:pageview(單線程:無競争)           

說明:假如一個使用者的id為123,初始pageview為0,别的使用者每浏覽一次123使用者的首頁,pageview自增1,這樣每個使用者id的通路量就進行了區分。

2.3 set指令和setnx指令

set key value           不管key是否存在,都進行設定
setnx key value         key不存在,才進行設定
set key value xx        key存在才設定           
127.0.0.1:6379> exists python
(integer) 1
127.0.0.1:6379> del python
(integer) 1
127.0.0.1:6379> exists python
(integer) 0
127.0.0.1:6379> set python good
OK
127.0.0.1:6379> setnx python good
(integer) 0
127.0.0.1:6379> set python base xx
OK
127.0.0.1:6379> get python
"base"
127.0.0.1:6379> exists python
(integer) 1
127.0.0.1:6379> 
127.0.0.1:6379> 
127.0.0.1:6379> exists java
(integer) 0
127.0.0.1:6379> setnx java easy
(integer) 1
127.0.0.1:6379> set java aaa xx
OK
127.0.0.1:6379> get java
"aaa"           
set指令和setnx指令的時間複雜度為O(1)           

2.4 mget指令和mset指令

mget key1 key2 key3                         批量擷取key,原子操作
mset key1 value1 key2 value2 key3 value3    批量設定key-value           
127.0.0.1:6379> mset hello world python best php easy
OK
127.0.0.1:6379> mget hello python php
1) "world"
2) "best"
3) "easy"           
1.mget指令和mset指令的時間複雜度為O(n)
2.使用get指令擷取某個key的值,server端計算後傳回對應的值給client端
此時如果想擷取n個key的值,需要傳輸n次,server端也需要計算n次,這樣所需要的時間為 n次get = n次網絡時間 + n次指令時間
3.如果使用mget指令一次傳遞n個key的值到server端,隻需要傳輸一次,server端計算之後,一次性把計算結果傳回給client端
這樣所需要的時間為:1次mget = 1次網絡時間 + n次指令時間
4.在很多場景中,使用mget指令的效率比get指令效率高很多,mget指令後接的key越多效率越明顯,但是當key的量很多時,可以對key進行拆分,分批擷取key的值,           

2.5 getset指令,append指令和strlen指令

getset key newvalue     set key newvalue并傳回舊的value
append key value        将value追加到舊的value
strlen key              傳回字元串的長度(注意中文)           
127.0.0.1:6379> set hello world
OK
127.0.0.1:6379> getset hello python
"world"
127.0.0.1:6379> append hello ',java'
(integer) 11
127.0.0.1:6379> get hello
"python,java"
127.0.0.1:6379> strlen(hello)
(error) ERR unknown command 'strlen(hello)'
127.0.0.1:6379> strlen hello
(integer) 11
127.0.0.1:6379> set hello '足球'
OK
127.0.0.1:6379> strlen hello
(integer) 6           
getset指令,append指令和strlen指令的時間複雜度為O(1)           

2.6 incrby指令,getrange指令和setrange指令

incrbyfloat key float       key自增float值
getrange key start end      擷取字元串指定下标所有的值
setrange key index value    設定指定下标所有對應的值           
127.0.0.1:6379> incr counter
(integer) 50
127.0.0.1:6379> del counter
(integer) 1
127.0.0.1:6379> incr counter
(integer) 1
127.0.0.1:6379> incrbyfloat counter 1.1
"2.1"
127.0.0.1:6379> get counter
"2.1"
127.0.0.1:6379> set hello pythonbest
OK
127.0.0.1:6379> getrange hello 0 6
"pythonb"
127.0.0.1:6379> getrange hello 0 5
"python"
127.0.0.1:6379> setrange hello 6 e
(integer) 10
127.0.0.1:6379> get hello
"pythoneest"           
incrby指令,getrange指令和setrange指令的時間複雜度為O(1)