Java 8 redis集合原子lpop all
redis列表,一个制作人保存lpush。在另一个线程中,使用者定期从列表中取出所有内容,并对元素进行分类。因为制作人一直在推动,所以所有的拍摄都必须原子化完成。那么有没有一种有效的方法来做到这一点呢可以使用spring data redisJava 8 redis集合原子lpop all,java-8,redisclient,Java 8,Redisclient,redis列表,一个制作人保存lpush。在另一个线程中,使用者定期从列表中取出所有内容,并对元素进行分类。因为制作人一直在推动,所以所有的拍摄都必须原子化完成。那么有没有一种有效的方法来做到这一点呢可以使用spring data redis // producer getOpsForList.push(k, v); // consumer alist = range(k,0,-1); // take all out alist.parallelStream() // during which
// producer
getOpsForList.push(k, v);
// consumer
alist = range(k,0,-1); // take all out
alist.parallelStream() // during which a producer thread could push but I hope it is "blocked".
delete(k); // list is now empty and push from producer is unblocked.
multi
和exec
无法实现我的目标,因为它实际上只在一个事务中提交lrange
、lpush
和delete
。到目前为止,我能想到的唯一方法是保持lpop
并将返回的add添加到alist
中,直到列表为空
编辑,这就是我的想法:
如果要确保操作只运行一次,请使用watch
:
watch key
val = get key
val = val + 1
multi
set key val
exec
当您希望不被“中断”(不是多线程中断)并且不关心它运行多少次时,事务(multi
和exec
)就足够了
multi
val = lrange key 0 -1
delete key
exec
val
完成后仍然是一个列表,就像在
事务中的所有命令都被序列化并执行
按顺序。由另一方发出的请求永远不会发生
客户端在ReIIS的执行过程中被服务
交易
在redis之外,我将数据操作list.stream.parallelism
取出,该函数现在只关注数据getter,这与最后一段代码完全相同
一个很好的例子说明了如何使用WATCH创建Redis不支持的新的原子操作,即实现ZPOP,这是一个以原子方式从排序集弹出分数较低的元素的命令
文档中有一个ZPOP
的实现,如下所示:
WATCH zset
element = ZRANGE zset 0 0
MULTI
ZREM zset element
EXEC
如果EXEC失败(即返回空回复),您需要做的是重复上述操作。生产者操作lpush是原子的,因此不需要使用命令。例如:
// consumer pesudo code
do {
watch(k);
transaction = multi();
alist = transaction.range(k,0,-1);
transaction.delete(k);
status = get status of transaction.exec();
} while(status == null);
alist.parallelStream()
一个很好的例子说明了如何使用WATCH创建Redis不支持的新的原子操作,即实现ZPOP,这是一个以原子方式从排序集弹出分数较低的元素的命令
文档中有一个ZPOP
的实现,如下所示:
WATCH zset
element = ZRANGE zset 0 0
MULTI
ZREM zset element
EXEC
如果EXEC失败(即返回空回复),您需要做的是重复上述操作。生产者操作lpush是原子的,因此不需要使用命令。例如:
// consumer pesudo code
do {
watch(k);
transaction = multi();
alist = transaction.range(k,0,-1);
transaction.delete(k);
status = get status of transaction.exec();
} while(status == null);
alist.parallelStream()
请把开场白放在评论里(如果有的话)。所以,这不是调情的地方,卡萨诺瓦@holi java watch将在监视目标未更改时提交执行。虽然这不是我想要的。我希望当消费者接受所有元素时,生产者的推送操作可以被阻止,并且只有在消费者完成时(即删除后)才能恢复。但我会将您的解决方案与lpop循环进行比较。@holi java producer随机但经常弹出。spring data redis具有
pushAll
,因此我正在寻找一种方法来实现popAll
@Tiina为什么制作人需要从列表中弹出元素?@Tiina如果您的要求是从消费者处弹出所有元素,您可以设置两个键,一个是offset
从0开始,另一个是n
,由llen
获得,然后,您可以使用管道弹出每个区块中的元素(例如:区块大小为100),直到偏移量>=n
。请将开头文本放入注释中(如果有)。所以,这不是调情的地方,卡萨诺瓦@holi java watch将在监视目标未更改时提交执行。虽然这不是我想要的。我希望当消费者接受所有元素时,生产者的推送操作可以被阻止,并且只有在消费者完成时(即删除后)才能恢复。但我会将您的解决方案与lpop循环进行比较。@holi java producer随机但经常弹出。spring data redis具有pushAll
,因此我正在寻找一种方法来实现popAll
@Tiina为什么制作人需要从列表中弹出元素?@Tiina如果您的要求是从消费者处弹出所有元素,您可以设置两个键,一个是offset
从0开始,另一个是n
,由llen
获得,然后,您可以使用管道来弹出每个块中的元素(例如:块大小为100),直到offset>=n
。