您好,登錄后才能下訂單哦!
這篇“Redis如何實現數據的交集、并集、補集”文章的知識點大部分人都不太理解,所以小編給大家總結了以下內容,內容詳細,步驟清晰,具有一定的借鑒價值,希望大家閱讀完這篇文章能有所收獲,下面我們一起來看看這篇“Redis如何實現數據的交集、并集、補集”文章吧。
今天我們來模擬一個這樣的場景,我們在本地有多個文本文件,每個文件里面存了很多的32位的字符串作為用戶的唯一標識,每個用戶存做一行,假如我們每天都有非常大規模的用戶,這樣我們可能在工作中就存在需要對這些用戶進行交集、并集或補集等處理,最簡單的方式是通過Java中的集合來進行運算即可,比如通過HashSet來進行相應的一些運算,但是這樣的運算存在一個局限性,那就是我們一般在JVM運行過程中初始的內存是有限的,這樣如果全部在JVM內存中進行計算的話,很容易出現內存空間不足導致的OOM異常,那么我們今天來介紹一種拓展性更強的方式來進行這樣的一些交并補的運算:通過Redis來實現數據的交集、并集、補集
Redis版本: Redis 6.0.6
Jedis版本: 4.2.2
工具類hutool版本: 5.8.0.M3
pom文件:
<dependencies> <dependency> <groupId>redis.clients</groupId> <artifactId>jedis</artifactId> <version>4.2.2</version> </dependency> <dependency> <groupId>cn.hutool</groupId> <artifactId>hutool-all</artifactId> <version>5.8.0.M3</version> </dependency> </dependencies>
初始化常量
public class RedisCalculateUtils { static String oneFileString = "/Users/tmp/test-1.txt"; static String twoFileString = "/Users/tmp/test-2.txt"; static String diffFileString = "/Users/tmp/diff-test.txt"; static String interFileString = "/Users/tmp/inter-test.txt"; static String unionFileString = "/Users/tmp/union-test.txt"; static String oneFileCacheKey = "oneFile"; static String twoFileCacheKey = "twoFile"; static String diffFileCacheKey = "diffFile"; static String interFileCacheKey = "interFile"; static String unionFileCacheKey = "unionFile"; }
初始化數據到指定文件
/** * 初始化數據并寫入文件中 */ public static void writeFile() { File oneFile = new File(oneFileString); List<String> fs = new ArrayList<>(10000); for (int i = 10000; i < 15000; i++) { String s = SecureUtil.md5(String.valueOf(i)); fs.add(s); } FileUtil.writeUtf8Lines(fs, oneFile); File twoFile = new File(twoFileString); fs.clear(); for (int i = 12000; i < 20000; i++) { String s = SecureUtil.md5(String.valueOf(i)); fs.add(s); } FileUtil.writeUtf8Lines(fs, twoFile); }
指定文件寫入Redis
/** * 讀取文件數據并寫入Redis */ public static void writeCache() { try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { Pipeline p = jedis.pipelined(); List<String> oneFileStringList = FileUtil.readLines(oneFileString, "UTF-8"); for (String s : oneFileStringList) { p.sadd(oneFileCacheKey, s); } p.sync(); List<String> twoFileStringList = FileUtil.readLines(twoFileString, "UTF-8"); for (String s : twoFileStringList) { p.sadd(twoFileCacheKey, s); } p.sync(); } catch (Exception e) { throw new RuntimeException(e); } }
/** * oneKey對應的Set 與 twoKey對應的Set 的差集 并寫入 threeKey * @param oneKey 差集前面的集合Key * @param twoKey 差集后面的集合Key * @param threeKey 差集結果的集合Key */ public static void diff(String oneKey, String twoKey, String threeKey) { try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { long result = jedis.sdiffstore(threeKey, oneKey, twoKey); System.out.println("oneKey 與 twoKey 的差集的個數:" + result); } catch (Exception e) { throw new RuntimeException(e); } }
差集計算結果寫入到指定文件
/** * 將計算的差集數據寫入到指定文件 */ public static void writeDiffToFile() { File diffFile = new File(diffFileString); try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { Set<String> result = jedis.smembers(diffFileCacheKey); FileUtil.writeUtf8Lines(result, diffFile); } catch (Exception e) { throw new RuntimeException(e); } }
/** * * @param cacheKeyArray 交集集合Key * @param destinationKey 交集集合結果Key */ public static void inter(String[] cacheKeyArray, String destinationKey) { try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { long result = jedis.sinterstore(destinationKey, cacheKeyArray); System.out.println("cacheKeyArray 的交集的個數:" + result); } catch (Exception e) { throw new RuntimeException(e); } }
交集計算結果寫入指定文件
/** * 將計算的交集數據寫入到指定文件 */ public static void writeInterToFile() { File interFile = new File(interFileString); try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { Set<String> result = jedis.smembers(interFileCacheKey); FileUtil.writeUtf8Lines(result, interFile); } catch (Exception e) { throw new RuntimeException(e); } }
/** * 計算多個Key的并集并寫入到新的Key * @param cacheKeyArray 求并集的Key * @param destinationKey 并集結果寫入的KEY */ public static void union(String[] cacheKeyArray, String destinationKey) { try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { long result = jedis.sunionstore(destinationKey, cacheKeyArray); System.out.println("cacheKeyArray 的并集的個數:" + result); } catch (Exception e) { throw new RuntimeException(e); } }
并集計算結果寫入到指定文件
/** * 將計算的并集數據寫入到指定文件 */ public static void writeUnionToFile() { File unionFile = new File(unionFileString); try(Jedis jedis = new Jedis("127.0.0.1", 6379)) { Set<String> result = jedis.smembers(unionFileCacheKey); FileUtil.writeUtf8Lines(result, unionFile); } catch (Exception e) { throw new RuntimeException(e); } }
SDIFFSTORE destination key [key …]
舉例說明:
key1 = {a,b,c,d} key2 = {c} key3 = {a,c,e} SDIFF key1 key2 key3 = {b,d}
SDIFFSTORE 命令的作用和SDIFF類似,不同的是它將結果保存到 destination 集合,而把結果集返回給客戶端。
如果 destination 集合已經存在,則將其覆蓋。
返回值
結果集中成員數量
SINTERSTORE destination key [key …]
舉例說明:
key1 = {a,b,c,d} key2 = {c} key3 = {a,c,e} SINTER key1 key2 key3 = {c}
SINTERSTORE 命令與 SINTER 命令類似,不同的是它并不是直接返回結果集,而是將結果保存在 destination 集合中。
如果 destination 集合存在, 則會被覆蓋。
返回值
結果集中成員數量
SUNIONSTORE destination key [key …]
舉例說明:
key1 = {a,b,c,d} key2 = {c} key3 = {a,c,e} SUNION key1 key2 key3 = {a,b,c,d,e}
SUNIONSTORE 命令的功能類似于 SUNION,不同的是不反回結果集,而是存儲在 destination 中。
如果 destination 已經存在,則被覆蓋。
返回值
結果集中的成員數量
以上就是關于“Redis如何實現數據的交集、并集、補集”這篇文章的內容,相信大家都有了一定的了解,希望小編分享的內容對大家有幫助,若想了解更多相關的知識內容,請關注億速云行業資訊頻道。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。