Redis Lua 脚本解包返回不同的结果

Posted

技术标签:

【中文标题】Redis Lua 脚本解包返回不同的结果【英文标题】:Redis Lua Script Unpack Returning Different Results 【发布时间】:2016-07-14 21:41:10 【问题描述】:

通过运行 sadd a b c 进行设置

当我对集合执行此代码时 keytoclear1 中只有一个值“b”。 keytoclear2 作为其中的两个值。

local keystoclear = unpack(redis.call('smembers', KEYS[1]))

redis.call('sadd', 'keystoclear1', keystoclear)

redis.call('sadd', 'keystoclear2', unpack(redis.call('smembers', KEYS[1])))

我绝不是 lua 专家,所以我可能会在这里遇到一些奇怪的行为,但我想知道是什么原因造成的。

我使用 redis-cli 和 stackexchange.redis 客户端在 windows 和 linux 版本的 redis 上对此进行了测试。在所有情况下都有相同的行为。这是一个简单的例子,我实际上想存储解包的结果,因为我需要用它执行几个操作。

更新:我理解这个问题。

table.unpack() only returns the first element

Lua 总是根据调用的情况调整函数的结果数量。当我们将函数作为语句调用时,Lua 会丢弃它的所有结果。当我们使用调用作为表达式时,Lua 只保留第一个结果。只有当调用是表达式列表中的最后一个(或唯一的)表达式时,我们才会得到所有结果。

【问题讨论】:

【参考方案1】:

此案例与您在更新中引用的案例略有不同。在这种情况下unpack(可能)返回几个元素,但您只存储一个并丢弃其余元素。如果你使用local keytoclear1, keytoclear2 = ...,你可以获得其他元素,但是存储表格本身并根据需要解包要容易得多:

local keystoclear = redis.call('smembers', KEYS[1])
redis.call('sadd', 'keystoclear1', unpack(keystoclear))

只要unpack 是最后一个参数,您就会得到解压缩表中存在的所有元素。

【讨论】:

尝试拨打redis.call('sadd', 'keystoclear1', (unpack(keystoclear))) @moteus,这将为您提供keystoclear 中的第一个元素,这就是 OP 现在所拥有的。

以上是关于Redis Lua 脚本解包返回不同的结果的主要内容,如果未能解决你的问题,请参考以下文章

Redis中使用Lua

使用 RedisTemplate 执行 lua 脚本时结果令人困惑

Redis 在Golang中使用遇到的坑

python redis客户端使用lua脚本

如何并行运行单个Lua脚本对多个Redis值?

Redis中使用Lua脚本