/** * SortedSet(有序集合) * ZADD,ZCARD,ZCOUNT,ZINCRBY,ZRANGE,ZRANGEBYSCORE,ZRANK,ZREM,ZREMRANGEBYRANK,ZREMRANGEBYSCORE,ZREVRANGE * ZREVRANGEBYSCORE,ZREVRANK,ZSCORE,ZUNIONSTORE,ZINTERSTORE,ZSCAN,ZRANGEBYLEX,ZLEXCOUNT,ZREMRANGEBYLEX */ public class SortedSetTypeTest { private Jedis jedis; private static final String KEY = "sorted_set"; private static final String VALUE = "layman"; @Before public void setUp() { this.jedis = new Jedis(new JedisShardInfo("192.168.133.188", 6379)); } /** * ZADD key score member [[score member] [score member] ...] * 將一個或多個 member 元素及其 score 值加入到有序集 key 當中。 * 若是某個 member 已是有序集的成員,那麼更新這個 member 的 score 值,並經過從新插入這個 member 元素,來保證該 member 在正確的位置上。 * score 值能夠是整數值或雙精度浮點數。 * 若是 key 不存在,則建立一個空的有序集並執行 ZADD 操做。 * 當 key 存在但不是有序集類型時,返回一個錯誤。 */ @Test public void ZADD() { Map<String, Double> sourceMember = new HashMap<String, Double>(); for (int i = 0; i < 3; i++) { double score = getRandomInt(); sourceMember.put(VALUE + score, score); } jedis.zadd(KEY, sourceMember); ZRANGE(); } /** * ZCARD key * 返回有序集 key 的基數。 */ @Test public void ZCARD() { System.out.println(jedis.zcard(KEY)); } /** * ZCOUNT key min max * 返回有序集 key 中, score 值在 min 和 max 之間(默認包括 score 值等於 min 或 max )的成員的數量。 * 關於參數 min 和 max 的詳細使用方法,請參考 ZRANGEBYSCORE 命令。 */ @Test public void ZCOUNT() { System.out.println(jedis.zcount(KEY, "-inf", "+inf")); System.out.println(jedis.zcount(KEY, 24, 45)); } /** * ZINCRBY key increment member * 爲有序集 key 的成員 member 的 score 值加上增量 increment 。 * 能夠經過傳遞一個負數值 increment ,讓 score 減去相應的值,好比 ZINCRBY key -5 member ,就是讓 member 的 score 值減去 5 。 * 當 key 不存在,或 member 不是 key 的成員時, ZINCRBY key increment member 等同於 ZADD key increment member 。 * 當 key 不是有序集類型時,返回一個錯誤。 * score 值能夠是整數值或雙精度浮點數。 */ @Test public void ZINCRBY() { ZRANGE(); // jedis.zincrby(KEY, getRandomInt(), VALUE + 10); // ZRANGE(); jedis.zincrby(KEY, 20, VALUE + 10); ZRANGE(); } /** * ZRANGE key start stop [WITHSCORES] * 返回有序集 key 中,指定區間內的成員。 * 其中成員的位置按 score 值遞增(從小到大)來排序。 * 具備相同 score 值的成員按字典序(lexicographical order )來排列。 * 若是你須要成員按 score 值遞減(從大到小)來排列,請使用 ZREVRANGE 命令。 * 下標參數 start 和 stop 都以 0 爲底,也就是說,以 0 表示有序集第一個成員,以 1 表示有序集第二個成員,以此類推。 * 你也能夠使用負數下標,以 -1 表示最後一個成員, -2 表示倒數第二個成員,以此類推。 * 超出範圍的下標並不會引發錯誤。 * 好比說,當 start 的值比有序集的最大下標還要大,或是 start > stop 時, ZRANGE 命令只是簡單地返回一個空列表。 * 另外一方面,假如 stop 參數的值比有序集的最大下標還要大,那麼 Redis 將 stop 看成最大下標來處理。 * 能夠經過使用 WITHSCORES 選項,來讓成員和它的 score 值一併返回,返回列表以 value1,score1, ..., valueN,scoreN 的格式表示。 * 客戶端庫可能會返回一些更復雜的數據類型,好比數組、元組等。 * <p/> * ZREVRANGE key start stop [WITHSCORES] * 返回有序集 key 中,指定區間內的成員。 * 其中成員的位置按 score 值遞減(從大到小)來排列。 * 具備相同 score 值的成員按字典序的逆序(reverse lexicographical order)排列。 * 除了成員按 score 值遞減的次序排列這一點外, ZREVRANGE 命令的其餘方面和 ZRANGE 命令同樣。 */ @Test public void ZRANGE() { // System.out.println(jedis.zrange(KEY, 0, -1)); Set<Tuple> tuples = jedis.zrangeWithScores(KEY, 0, -1); for (Tuple tuple : tuples) { System.out.println(tuple.getElement() + ":" + tuple.getScore()); } } /** * ZRANGEBYSCORE key min max [WITHSCORES] [LIMIT offset count] * 返回有序集 key 中,全部 score 值介於 min 和 max 之間(包括等於 min 或 max )的成員。有序集成員按 score 值遞增(從小到大)次序排列。 * 具備相同 score 值的成員按字典序(lexicographical order)來排列(該屬性是有序集提供的,不須要額外的計算)。 * 可選的 LIMIT 參數指定返回結果的數量及區間(就像SQL中的 SELECT LIMIT offset, count ),注意當 offset 很大時,定位 offset 的操做可能須要遍歷整個有序集,此過程最壞複雜度爲 O(N) 時間。 * 可選的 WITHSCORES 參數決定結果集是單單返回有序集的成員,仍是將有序集成員及其 score 值一塊兒返回。 * 該選項自 Redis 2.0 版本起可用。 * 區間及無限 * min 和 max 能夠是 -inf 和 +inf ,這樣一來,你就能夠在不知道有序集的最低和最高 score 值的狀況下,使用 ZRANGEBYSCORE 這類命令。 * 默認狀況下,區間的取值使用閉區間 (小於等於或大於等於),你也能夠經過給參數前增長 ( 符號來使用可選的開區間 (小於或大於)。 * <p/> * ZREVRANGEBYSCORE key max min [WITHSCORES] [LIMIT offset count] * 返回有序集 key 中, score 值介於 max 和 min 之間(默認包括等於 max 或 min )的全部的成員。有序集成員按 score 值遞減(從大到小)的次序排列。 * 具備相同 score 值的成員按字典序的逆序(reverse lexicographical order )排列。 * 除了成員按 score 值遞減的次序排列這一點外, ZREVRANGEBYSCORE 命令的其餘方面和 ZRANGEBYSCORE 命令同樣。 */ @Test public void ZRANGEBYSCORE() { System.out.println(jedis.zrangeByScore(KEY, 0, 100)); System.out.println(jedis.zrangeByScore(KEY, 0, 100, 8, 15)); System.out.println(jedis.zrangeByScore(KEY, "-inf", "+inf")); System.out.println(jedis.zrangeByScore(KEY, "-inf", "+inf", 8, 1)); Set<Tuple> tuples = jedis.zrangeByScoreWithScores(KEY, "-inf", "+inf", 8, 1); for (Tuple tuple : tuples) { System.out.println(tuple.getElement() + "=" + tuple.getScore()); } } /** * ZRANK key member * 返回有序集 key 中成員 member 的排名。其中有序集成員按 score 值遞增(從小到大)順序排列。 * 排名以 0 爲底,也就是說, score 值最小的成員排名爲 0 。 * 使用 ZREVRANK 命令能夠得到成員按 score 值遞減(從大到小)排列的排名。 * <p/> * ZREVRANK key member * 返回有序集 key 中成員 member 的排名。其中有序集成員按 score 值遞減(從大到小)排序。 * 排名以 0 爲底,也就是說, score 值最大的成員排名爲 0 。 * 使用 ZRANK 命令能夠得到成員按 score 值遞增(從小到大)排列的排名。 */ @Test public void ZRANK() { System.out.println(jedis.zrank(KEY, "layman56.0")); } /** * ZREM key member [member ...] * 移除有序集 key 中的一個或多個成員,不存在的成員將被忽略。 * 當 key 存在但不是有序集類型時,返回一個錯誤。 */ @Test public void ZREM() { ZRANGE(); jedis.zrem(KEY, "layman72.0", "layman77.0"); System.out.println("######################"); ZRANGE(); } /** * ZREMRANGEBYRANK key start stop * 移除有序集 key 中,指定排名(rank)區間內的全部成員。 * 區間分別如下標參數 start 和 stop 指出,包含 start 和 stop 在內。 * 下標參數 start 和 stop 都以 0 爲底,也就是說,以 0 表示有序集第一個成員,以 1 表示有序集第二個成員,以此類推。 * 你也能夠使用負數下標,以 -1 表示最後一個成員, -2 表示倒數第二個成員,以此類推。 */ @Test public void ZREMRANGEBYRANK() { ZRANGE(); jedis.zremrangeByRank(KEY, 0, 1); System.out.println("##################"); ZRANGE(); } /** * ZREMRANGEBYSCORE key min max * 移除有序集 key 中,全部 score 值介於 min 和 max 之間(包括等於 min 或 max )的成員。 * 自版本2.1.6開始, score 值等於 min 或 max 的成員也能夠不包括在內,詳情請參見 ZRANGEBYSCORE 命令。 */ @Test public void ZREMRANGEBYSCORE() { ZRANGE(); jedis.zremrangeByScore(KEY, "53", "63");//刪除53<score<63 System.out.println("#####################"); ZRANGE(); } /** * ZSCORE key member * 返回有序集 key 中,成員 member 的 score 值。 * 若是 member 元素不是有序集 key 的成員,或 key 不存在,返回 nil 。 */ @Test public void ZSCORE() { System.out.println(jedis.zscore(KEY, "layman84.0")); } /** * ZUNIONSTORE destination numkeys key [key ...] [WEIGHTS weight [weight ...]] [AGGREGATE SUM|MIN|MAX] * 計算給定的一個或多個有序集的並集,其中給定 key 的數量必須以 numkeys 參數指定,並將該並集(結果集)儲存到 destination 。 * 默認狀況下,結果集中某個成員的 score 值是全部給定集下該成員 score 值之 和 。 * WEIGHTS * 使用 WEIGHTS 選項,你能夠爲 每一個 給定有序集 分別 指定一個乘法因子(multiplication factor), * 每一個給定有序集的全部成員的 score 值在傳遞給聚合函數(aggregation function)以前都要先乘以該有序集的因子。 * 若是沒有指定 WEIGHTS 選項,乘法因子默認設置爲 1 。 * AGGREGATE * 使用 AGGREGATE 選項,你能夠指定並集的結果集的聚合方式。 * 默認使用的參數 SUM ,能夠將全部集合中某個成員的 score 值之 和 做爲結果集中該成員的 score 值;使用參數 MIN , * 能夠將全部集合中某個成員的最小score值做爲結果集中該成員的score值;而參數MAX則是將全部集合中某個成員的最大score值做爲結果集中該成員的score值。 */ @Test public void ZUNIONSTORE() { ZADDForKey(KEY + 0); ZRANGE(); System.out.println("###############################"); System.out.println(jedis.zrange(KEY + 0, 0, -1)); ZParams zParams = new ZParams(); zParams.aggregate(ZParams.Aggregate.MAX); // zParams.weightsByDouble(1); jedis.zunionstore(KEY, zParams, KEY, KEY + 0); System.out.println("###############################"); System.out.println(jedis.zrange(KEY, 0, -1)); } /** * ZINTERSTORE destination numkeys key [key ...] [WEIGHTS weight [weight ...]] [AGGREGATE SUM|MIN|MAX] * 計算給定的一個或多個有序集的交集,其中給定 key 的數量必須以 numkeys 參數指定,並將該交集(結果集)儲存到 destination 。 * 默認狀況下,結果集中某個成員的 score 值是全部給定集下該成員 score 值之和. * 關於 WEIGHTS 和 AGGREGATE 選項的描述,參見 ZUNIONSTORE 命令。 */ @Test public void ZINTERSTORE() { System.out.println(jedis.zrange(KEY, 0, -1)); System.out.println("###############################"); ZParams zParams = new ZParams(); zParams.aggregate(ZParams.Aggregate.MIN); // zParams.weightsByDouble(1d); System.out.println(jedis.zrange(KEY + 0, 0, -1)); jedis.zinterstore(KEY, zParams, KEY, KEY + 0); System.out.println("###############################"); System.out.println(jedis.zrange(KEY, 0, -1)); } /** * ZRANGEBYLEX key min max [LIMIT offset count] * 當有序集合的全部成員都具備相同的分值時, 有序集合的元素會根據成員的字典序(lexicographical ordering)來進行排序, * 而這個命令則能夠返回給定的有序集合鍵 key 中, 值介於 min 和 max 之間的成員。 * 若是有序集合裏面的成員帶有不一樣的分值, 那麼命令返回的結果是未指定的(unspecified)。 * 命令會使用 C 語言的 memcmp() 函數, 對集合中的每一個成員進行逐個字節的對比(byte-by-byte compare), 並按照從低到高的順序, 返回排序後的集合成員。 * 若是兩個字符串有一部份內容是相同的話, 那麼命令會認爲較長的字符串比較短的字符串要大。 * 可選的 LIMIT offset count 參數用於獲取指定範圍內的匹配元素 (就像 SQL 中的 SELECT LIMIT offset count 語句)。 須要注意的一點是, * 若是 offset 參數的值很是大的話, 那麼命令在返回結果以前, 須要先遍歷至 offset 所指定的位置, 這個操做會爲命令加上最多 O(N) 複雜度。 * 如何指定範圍區間 * 合法的 min 和 max 參數必須包含 ( 或者 [ , 其中 ( 表示開區間(指定的值不會被包含在範圍以內), 而 [ 則表示閉區間(指定的值會被包含在範圍以內)。 * 特殊值 + 和 - 在 min 參數以及 max 參數中具備特殊的意義, 其中 + 表示正無限, 而 - 表示負無限。 所以, 向一個全部成員的分值都相同的有序集合發送命令 * ZRANGEBYLEX <zset> - + , 命令將返回有序集合中的全部元素。 */ @Test public void ZRANGEBYLEX() { /** * redis> ZADD myzset 0 a 0 b 0 c 0 d 0 e 0 f 0 g (integer) 7 redis> ZRANGEBYLEX myzset - [c 1) "a" 2) "b" 3) "c" redis> ZRANGEBYLEX myzset - (c 1) "a" 2) "b" redis> ZRANGEBYLEX myzset [aaa (g 1) "b" 2) "c" 3) "d" 4) "e" 5) "f" */ ZRANGE(); System.out.println(jedis.zrangeByLex(KEY, "-", "+")); System.out.println(jedis.zrangeByLex(KEY, "-", "+", 1, 2)); } /** * ZLEXCOUNT key min max * 對於一個全部成員的分值都相同的有序集合鍵 key 來講, 這個命令會返回該集合中, 成員介於 min 和 max 範圍內的元素數量。 * 這個命令的 min 參數和 max 參數的意義和 ZRANGEBYLEX 命令的 min 參數和 max 參數的意義同樣。 */ @Test public void ZLEXCOUNT() { System.out.println(jedis.zlexcount(KEY, "-", "+")); } /** * ZREMRANGEBYLEX key min max * 對於一個全部成員的分值都相同的有序集合鍵 key 來講, 這個命令會移除該集合中, 成員介於 min 和 max 範圍內的全部元素。 * 這個命令的 min 參數和 max 參數的意義和 ZRANGEBYLEX 命令的 min 參數和 max 參數的意義同樣。 */ @Test public void ZREMRANGEBYLEX() { ZRANGE(); jedis.zremrangeByLex(KEY, "-", "+"); System.out.println("#################"); ZRANGE(); } private int getRandomInt() { return new Random().nextInt(100); } private void ZADDForKey(String key) { if (StringUtils.isEmpty(key)) { key = KEY; } Map<String, Double> sourceMember = new HashMap<String, Double>(); for (int i = 0; i < 3; i++) { double score = getRandomInt(); sourceMember.put(VALUE + score, score); } jedis.zadd(key, sourceMember); } }