三種特殊數(shù)據(jù)類型
Geospatial 地理位置
只有六個(gè)命令:

# getadd 添加地理位置
# 規(guī)則:兩級無法直接添加,我們一般會下載城市數(shù)據(jù),直接通過java程序一次性導(dǎo)入!
# 有效的經(jīng)度從-180度到180度。
# 有效的緯度從-85.05112878度到85.05112878度。
# 當(dāng)坐標(biāo)位置超出上述指定范圍時(shí),該命令將會返回一個(gè)錯(cuò)誤。
# 127.0.0.1:6379> geoadd china:city 39.90 116.40 beijin
(error) ERR invalid longitude,latitude pair 39.900000,116.400000
# 參數(shù) key 值()
127.0.0.1:6379> geoadd china:city 116.40 39.90 beijing
(integer) 1
127.0.0.1:6379> geoadd china:city 121.47 31.23 shanghai
(integer) 1
127.0.0.1:6379> geoadd china:city 106.50 29.53 chongqi 114.05 22.52 shengzhen
(integer) 2
127.0.0.1:6379> geoadd china:city 120.16 30.24 hangzhou 108.96 34.26 xian
(integer) 2
###########################################
# getpos獲得當(dāng)前定位:一定是一個(gè)坐標(biāo)值!
127.0.0.1:6379> GEOPOS china:city beijing # 獲取指定的城市的經(jīng)度和緯度!
1) 1) "116.39999896287918091"
2) "39.90000009167092543"
127.0.0.1:6379> GEOPOS china:city beijing chongqi
1) 1) "116.39999896287918091"
2) "39.90000009167092543"
2) 1) "106.49999767541885376"
2) "29.52999957900659211"
###########################################
# GEODIST兩人之間的距離!
#單位:
# m 表示單位為米。
# km 表示單位為千米。
# mi 表示單位為英里。
# ft 表示單位為英尺。
127.0.0.1:6379> GEODIST china:city beijing shanghai km # 查看上海到北京的直線距離
"1067.3788"
127.0.0.1:6379> GEODIST china:city beijing chongqi km # 查看重慶到北京的直線距離
"1464.0708"
###########################################
#georadius 以給定的經(jīng)緯度為中心, 找出某一半徑內(nèi)的元素
127.0.0.1:6379> GEORADIUS china:city 110 30 1000 km # 以110,30 這個(gè)經(jīng)緯度為中心,尋
找方圓1000km內(nèi)的城市
1) "chongqi"
2) "xian"
3) "shengzhen"
4) "hangzhou"
127.0.0.1:6379> GEORADIUS china:city 110 30 500 km
1) "chongqi"
2) "xian"
127.0.0.1:6379> GEORADIUS china:city 110 30 500 km withdist # 顯示到中間距離的位置
1) 1) "chongqi"
2) "341.9374"
2) 1) "xian"
2) "483.8340"
127.0.0.1:6379> GEORADIUS china:city 110 30 500 km withcoord # 顯示他人的定位信息
1) 1) "chongqi"
2) 1) "106.49999767541885376"
2) "29.52999957900659211"
2) 1) "xian"
2) 1) "108.96000176668167114"
2) "34.25999964418929977"
127.0.0.1:6379> GEORADIUS china:city 110 30 500 km withdist withcoord count 1 # 篩選出指定的結(jié)果!
1) 1) "chongqi"
2) "341.9374"
3) 1) "106.49999767541885376"
2) "29.52999957900659211"
127.0.0.1:6379> GEORADIUS china:city 110 30 500 km withdist withcoord count 2
1) 1) "chongqi"
2) "341.9374"
3) 1) "106.49999767541885376"
2) "29.52999957900659211"
2) 1) "xian"
2) "483.8340"
3) 1) "108.96000176668167114"
2) "34.25999964418929977"
# 找出位于指定元素周圍的其他元素!
127.0.0.1:6379> GEORADIUSBYMEMBER china:city beijing 1000 km
1) "beijing"
2) "xian"
127.0.0.1:6379> GEORADIUSBYMEMBER china:city shanghai 400 km
1) "hangzhou"
2) "shanghai"
###########################################
#GEOHASH 命令 - 返回一個(gè)或多個(gè)位置元素的 Geohash 表示
# 將二維的經(jīng)緯度轉(zhuǎn)換為一維的字符串,如果兩個(gè)字符串越接近,那么則距離越近!
127.0.0.1:6379> geohash china:city beijing chongqi
1) "wx4fbxxfke0"
2) "wm5xzrybty0"
#GEO 底層的實(shí)現(xiàn)原理其實(shí)就是 Zset!我們可以使用Zset命令來操作geo!
127.0.0.1:6379> ZRANGE china:city 0 -1 # 查看地圖中全部的元素
1) "chongqi"
2) "xian"
3) "shengzhen"
4) "hangzhou"
5) "shanghai"
6) "beijing"
127.0.0.1:6379> zrem china:city beijing # 移除指定元素!
(integer) 1
127.0.0.1:6379> ZRANGE china:city 0 -1
1) "chongqi"
2) "xian"
3) "shengzhen"
4) "hangzhou"
5) "shanghai"
Hyperloglog
優(yōu)點(diǎn):占用的內(nèi)存是固定,2^64 不同的元素的技術(shù),只需要廢 12KB內(nèi)存!如果要從內(nèi)存角度來比較的
話 Hyperloglog 首選!
27.0.0.1:6379> PFadd mykey a b c d e f g h i j # 創(chuàng)建第一組元素 mykey
(integer) 1
127.0.0.1:6379> PFCOUNT mykey # 統(tǒng)計(jì) mykey 元素的基數(shù)數(shù)量
(integer) 10
127.0.0.1:6379> PFadd mykey2 i j z x c v b n m # 創(chuàng)建第二組元素 mykey2
(integer) 1
127.0.0.1:6379> PFCOUNT mykey2
(integer) 9
127.0.0.1:6379> PFMERGE mykey3 mykey mykey2 # 合并兩組 mykey mykey2 => mykey3 并集
OK
127.0.0.1:6379> PFCOUNT mykey3 # 看并集的數(shù)量!
(integer) 15
Bitmap

位存儲
統(tǒng)計(jì)用戶信息,活躍,不活躍! 登錄 、 未登錄! 打卡,365打卡! 兩個(gè)狀態(tài)的,都可以使用
Bitmaps!
Bitmap 位圖,數(shù)據(jù)結(jié)構(gòu)! 都是操作二進(jìn)制位來進(jìn)行記錄,就只有0 和 1 兩個(gè)狀態(tài)!
365 天 = 365 bit 1字節(jié) = 8bit 46 個(gè)字節(jié)左右!
使用bitmap 來記錄 周一到周日的打卡!
周一:1 周二:0 周三:0 周四:1 ......
127.0.0.1:6379> SETBIT sign 0 1
(integer) 0
127.0.0.1:6379> SETBIT sign 1 0
(integer) 0
127.0.0.1:6379> SETBIT sign 2 0
(integer) 0
127.0.0.1:6379> SETBIT sign 3 1
(integer) 0
127.0.0.1:6379> SETBIT sign 4 1
(integer) 0
127.0.0.1:6379> SETBIT sign 5 0
(integer) 0
127.0.0.1:6379> SETBIT sign 6 0
(integer) 0
127.0.0.1:6379> GETBIT sign 3 # 查看某一天是否有打卡!
(integer) 1
127.0.0.1:6379> GETBIT sign 6
(integer) 0
127.0.0.1:6379> BITCOUNT sign # 統(tǒng)計(jì)這周的打卡記錄,就可以看到是否有全勤!
(integer) 3
事務(wù)
Redis 事務(wù)本質(zhì):一組命令的集合, 一個(gè)事務(wù)中的所有命令都會被序列化,在事務(wù)執(zhí)行過程的中,會按
照順序執(zhí)行!
一次性、順序性、排他性!執(zhí)行一些列的命令!
Redis事務(wù)沒有沒有隔離級別的概念!
所有的命令在事務(wù)中,并沒有直接被執(zhí)行!只有發(fā)起執(zhí)行命令的時(shí)候才會執(zhí)行!Exec
Redis單條命令式保存原子性的,但是事務(wù)不保證原子性!
redis的事務(wù):
- 開啟事務(wù)(multi)
- 命令入隊(duì)(......)
- 執(zhí)行事務(wù)(exec)
正常執(zhí)行事務(wù)!
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> SET k1 v1
QUEUED
127.0.0.1:6379> SET k2 v2
QUEUED
127.0.0.1:6379> GET k2
QUEUED
127.0.0.1:6379> SET k3 v3
QUEUED
127.0.0.1:6379> EXEC
1) OK
2) OK
3) "v2"
4) OK
放棄事務(wù)
127.0.0.1:6379> MULTI # 開啟事務(wù)
OK
127.0.0.1:6379> SET k1 v1
QUEUED
127.0.0.1:6379> SET k2 v2
QUEUED
127.0.0.1:6379> SET k4 v4
QUEUED
127.0.0.1:6379> DISCARD # 取消事務(wù)
OK
127.0.0.1:6379> GET k4 # 事務(wù)隊(duì)列中命令都不會被執(zhí)行!
(nil)
編譯型異常(代碼有問題! 命令有錯(cuò)?。?,事務(wù)中所有的命令都不會被執(zhí)行!
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> SET k1 v1
QUEUED
127.0.0.1:6379> SET k2 v2
QUEUED
127.0.0.1:6379> SET k3 v3
QUEUED
127.0.0.1:6379> getset k3 # 錯(cuò)誤的命令
(error) ERR wrong number of arguments for 'getset' command
127.0.0.1:6379> SET k4 v4
QUEUED
127.0.0.1:6379> SET k5 v5
QUEUED
127.0.0.1:6379> EXEC # 執(zhí)行事務(wù)報(bào)錯(cuò)!
(error) EXECABORT Transaction discarded because of previous errors.
127.0.0.1:6379> GET k5 # 所有的命令都不會被執(zhí)行!
(nil)
運(yùn)行時(shí)異常, 如果事務(wù)隊(duì)列中存在語法性,那么執(zhí)行命令的時(shí)候,其他命令是可以正常執(zhí)行的,錯(cuò)誤命令拋出異常!
127.0.0.1:6379> SET k1 "v1"
OK
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> INCR k1 # 會執(zhí)行的時(shí)候失敗!
QUEUED
127.0.0.1:6379> SET k2 v2
QUEUED
127.0.0.1:6379> SET k3 v3
QUEUED
127.0.0.1:6379> GET k3
QUEUED
127.0.0.1:6379> EXEC
1) (error) ERR value is not an integer or out of range # 雖然第一條命令報(bào)錯(cuò)了,但是依舊正常執(zhí)行成功了!
2) OK
3) OK
4) "v3"
127.0.0.1:6379> GET k2
"v2"
127.0.0.1:6379> GET k3
"v3"
Watch(監(jiān)控)
正常測試
127.0.0.1:6379> SET money 100
OK
127.0.0.1:6379> SET out 0
OK
127.0.0.1:6379> WATCH money # 監(jiān)視 money 對象
OK
127.0.0.1:6379> MULTI # 事務(wù)正常結(jié)束,數(shù)據(jù)期間沒有發(fā)生變動(dòng),這個(gè)時(shí)候就正常執(zhí)行成功!
OK
127.0.0.1:6379> DECRBY money 20
QUEUED
127.0.0.1:6379> INCRBY out 20
QUEUED
127.0.0.1:6379> EXEC
1) (integer) 80
2) (integer) 20
多客戶端修改
127.0.0.1:6379> WATCH money # 監(jiān)視 money
OK
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> DECRBY money 10
QUEUED
127.0.0.1:6379> INCRBY out 10
QUEUED
127.0.0.1:6379> EXEC # 執(zhí)行之前,另外一個(gè)線程,修改了我們的值,這個(gè)時(shí)候,就會導(dǎo)致事務(wù)執(zhí)行失?。?(nil)
如果修改失敗,先
unwatch解鎖,再重復(fù)上面的操作
127.0.0.1:6379> UNWATCH
OK
127.0.0.1:6379> WATCH money
OK
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379> DECRBY money 10
QUEUED
127.0.0.1:6379> INCRBY out 10
QUEUED
127.0.0.1:6379> EXEC
1) (integer) 1880
2) (integer) 30