1.2 分布式鎖
? ==原子操作==是指不回被線程調(diào)度機(jī)制打斷的操作。這種操作一旦開始追葡,就會一直運(yùn)行到結(jié)束赋除,中間不會有任何線程切換。
? Redis的分布式鎖不能解決超時問題初澎,鎖在任務(wù)執(zhí)行結(jié)束前就釋放了,另一個線程提前重新持有了這把鎖虑凛,導(dǎo)致任務(wù)無法嚴(yán)格串行執(zhí)行碑宴。為了避免這種問題,建議Redis分布式鎖不用用于較長時間的任務(wù)桑谍。
? 如果客戶端在處理請求時加鎖失敗怎么辦延柠?一般有以下三種策略:
- 直接拋出異常,通知用戶稍后重試
- sleep一會兒锣披,然后再重試
- 將請求轉(zhuǎn)移至延時隊列贞间,過一會再試
1.3 延時隊列
? Redis的list數(shù)據(jù)結(jié)構(gòu)常用來作為異步消息隊列使用,用rpush
和lpush
操作入隊列盈罐,用lpop
和rpop
操作出隊列榜跌。它可以支持多個生產(chǎn)者和多個消費(fèi)者并發(fā)進(jìn)出消息,每個消費(fèi)者拿的消息都是不同的列表元素盅粪。
? 延時隊列可以通關(guān)Redis的zset來實(shí)現(xiàn)。
1.4 位圖
? 位圖的最小單位是比特(bit)悄蕾,每個bit的取值只能是0或1票顾。
? Redis的位數(shù)組是自動擴(kuò)展的,如果設(shè)置了某個偏移位置超出了數(shù)組長度帆调,就會自動將位數(shù)組進(jìn)行零擴(kuò)充奠骄。
? Redis提供了位圖統(tǒng)計指令bitcount和位圖查找指令bitpos。bitcount用來統(tǒng)計指定位置范圍內(nèi)1的個數(shù)番刊,bitpos用來查找指定范圍內(nèi)出現(xiàn)的第一個0或1含鳞。
1.5 HyperLogLog
? Redis提供的HyperLogLog數(shù)據(jù)結(jié)構(gòu)可用來解決UV統(tǒng)計問題。HyperLogLog提供不精確的去重技術(shù)方案芹务,標(biāo)準(zhǔn)誤差率0.81%蝉绷。
? HyperLogLog提供了兩個指令pfadd
和pfcount
鸭廷,pfadd
是增加計數(shù),pfcount
獲取計數(shù)熔吗。
pubclic class pfTest{
public static void main(String[] args){
Jedis jedis = new Jedis();
for (int i = 0; i < 1000; i++){
jedis.pfadd("holle", "user" + i);
long total = jedis.pfcount("holle");
if (total != i + 1){
System.out.printf("%d %d\n", total, i + 1);
break;
}
}
jedis.close();
}
}
? HyperLogLog還提供了pfmerge
辆床,用于將多個pf計數(shù)值累加在一起形成一個新的pf值。
? HyperLogLog需要占據(jù)12KB的存儲空間桅狠,所以不適合統(tǒng)計單個用戶相關(guān)的數(shù)據(jù)讼载。