LoginSignup
15
9

More than 5 years have passed since last update.

RedisのZUNIONSTORE、ZINTERSTORE を理解する

Last updated at Posted at 2016-09-12

公式ドキュメントのZUNIONSTOREZINTERSTOREに書いてあるけれど、図解しないとわかりにくいと思います。

前提

私のSortedSetに対する理解の仕方について

私は、SortedSetをこのように理解しているので、そのつもりでお願いします。

このページで使用する、サンプルデータ

説明用に、事前に以下のように2つのSortedSetレコードを準備したことにします。

ZADD zset1 1 "one"
ZADD zset1 2 "two"
ZADD zset1 3 "three"

ZADD zset2 11 "one"
ZADD zset2 33 "three"
ZADD zset2 44 "four"

表にすると、各レコード(変数)は以下のようになってます。

縦軸にkey、横軸にmember、値がScoreです。

↓member\key→ zset1 zset2
one 1 11
two 2 (nil)
three 3 33
four (nil) 44

基本

Union(和集合)とかIntersect(共通集合)をして、Store(保存)します。デフォだと、各レコードにあるScoreを足し算します。

ミニマルな文法は、以下の通りです。

ZUNIONSTORE destination numkeys key [key ...]
ZINTERSTORE destination numkeys key [key ...]

  • distinationは、出力先のkey
  • numは、Union・IntersectしたいSortedSetの数
  • keyは、Union・IntersectしたいSortedSetのKey名

ZUNIONSTORE(和集合)の例

ZUNIONSTORE union1 2 zset1 zset2

これをやると、以下の表のようになります。

↓member\key→ zset1 zset2 union1
one 1 11 → 12
two 2 (nil) → 2
three 3 33 → 39
four (nil) 44 → 44

SortedSet常にScoreでソートされるので、以下のようになります。

ZRANGE union1 0 -1 WITHSCORES
1) "two"
2) "2"
3) "one"
4) "12"
5) "three"
6) "36"
7) "four"
8) "44"

ZINTERSTORE(共通集合)の例

ZINTERSTORE inter1 2 zset1 zset2

これをやると、以下の表のようになります。

↓member\key→ zset1 zset2 inter1
one 1 11 → 12
two 2 (nil) → (nil)
three 3 33 → 39
four (nil) 4 → (nil)

どうなってるか、確認してみます。

ZRANGE inter1 0 -1 WITHSCORES
1) "one"
2) "12"
3) "three"
4) "36"

各種オプション

UNIONとINTERSECTが何かはわかったと思うので、オプションはUNIONで説明します。(公式ドキュメントも、INTERSECTの方には「UNIONのほう見て」って書いてあるし。)

WEIGHTSオプション

keyに対するWEIGHTS(重み)オプションです。(この説明わかるのか…?)

ZUNIONSTOREZINTERSTOREに対するWEIGHTSの文法は、以下の通りです。

ZUNIONSTORE destination numkeys key [key ...] [WEIGHTS weight [weight ...]]
ZINTERSTORE destination numkeys key [key ...] [WEIGHTS weight [weight ...]]

…まぁ、同じですな。

  • weightは、keyと同じ数になります。

WEIGHTSオプションを使うとどうなるか

以下のようにやってみましょう。

ZUNIONSTORE union2 2 zset1 zset2 WEIGHTS 2 7

これをやると、以下の表のようになります。

↓member\key→ zset1(×2) zset2(×7) union2
one 1×2 11×7 → 79
two 2×2 (nil) → 4
three 3×2 33×7 → 237
four (nil) 44×7 → 308

SortedSetは、Scoreで常にソートされるので、以下のようになります。

ZRANGE union2 0 -1 WITHSCORES
1) "two"
2) "4"
3) "one"
4) "79"
5) "three"
6) "237"
7) "four"
8) "308"

AGGREGATEオプション

「基本」の説明で、以下のように書きました。

デフォだと、各レコードにあるScoreを足し算します。

この挙動を変更するオプションです。

このオプションの文法は、以下の通りです。

ZINTERSTORE destination numkeys key [key ...] [AGGREGATE SUM|MIN|MAX]
ZUNIONSTORE destination numkeys key [key ...] [AGGREGATE SUM|MIN|MAX]

例によって、同じです。

AGGREGATEオプションを使うとどうなるか

以下のようにやってみましょう。

ZUNIONSTORE union3 2 zset1 zset2 AGGREGATE MIN

AGGREGATE MIN としているので、小さいほうが選ばれます。

↓member\key→ zset1(×2) zset2(×7) union2
one 1 11 → 1
two 2 (nil) → 2
three 3 33 → 3
four (nil) 44 → 44
ZRANGE union3 0 -1 WITHSCORES
1) "one"
2) "1"
3) "two"
4) "2"
5) "three"
6) "3"
7) "four"
8) "44"

全部合わせてみる

最後に、4つのSortedSetに対して、適当にWEIGHTSAGGREGATE MAXを使った場合の例を載せておきます。

ZADD zset1 1 "one"
ZADD zset1 2 "two"
ZADD zset1 3 "three"

ZADD zset2 11 "one"
ZADD zset2 33 "three"
ZADD zset2 44 "four"

ZADD zset3 12 "one"
ZADD zset3 inf "three"
ZADD zset3 0 "four"

ZADD zset4 inf "one"
ZADD zset4 33 "three"


ZINTERSTORE inter4 4 zset1 zset2 zset3 zset4 WEIGHTS 13 1 1 0 AGGREGATE MAX
↓member\key→ zset1(×13) zset2(×1) zset3(×1) zset4(×0) inter4
one 1×13 11×1 12×1 inf×0 →13
two 2×13 (nil) (nil) (nil) →(nil)
three 3×13 33×1 inf×1 33×0 → inf
four (nil) 44×13 0×1 (nil) →(nil)
ZRANGE inter4 0 -1 WITHSCORES
1) "one"
2) "13"
3) "three"
4) "inf"

なるほど、WEIGHTSの演算結果で、Scoreの大きさを比較するんですね。

おわり

15
9
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
15
9