1、前提
因為項目需要redis一些老數據做刪除操作,大概30w數據,當時想的是用keys命令把數量一次性拿出來,但是keys會造成線程的阻塞,所以選擇使用scan命令進行操作
2、發現問題
當我在本地使用scan命令的時候,發現我測試環境明明有1000條數據,我每次count的條數是100條,但是驚奇的發現返回的總數居然不是100條,而是79條數據。
這個時候我就懷疑應該是我沒有理解到count機制的問題,然后就去翻閱官網,果然找到了答案。:
由此可以看到,count並不一定能返回用戶所指定的數量。既然如此,那么這個count到底做了什么尼。
3、在網上找到了一篇我認為還比較好的解答
從上面的解釋就可以看出,count其實並不是返回的是數量集合,而是查詢數據的時候進行的字典槽數量。
4、什么是字典槽
在 Redis 中所有的 key 都存儲在一個很大的字典中,這個字典的結構和 Java 中 的 HashMap 一樣,是一維數組 + 二維鏈表結構,
第一維數組的大小總是 2^n (n>=0),擴容一次數組大小空間加倍,也就是 n++。
scan 指令返回的游標就是第一維數組的位置索引,我們將這個位置索引稱為槽 (slot)。
如果不考慮字典的擴容縮容,直接按數組下標挨個遍歷就行了。
limit 參 數就表示需要遍歷的槽位數,之所以返回的結果可能多可能少,是因為不是所有 的槽位上都會掛接鏈表,
有些槽位可能是空的,還有些槽位上掛接的鏈表上的元 素可能會有多個。每
一次遍歷都會將 limit 數量的槽位上掛接的所有鏈表元素進 行模式匹配過濾后,一次性返回給客戶端。