使用Redis实现并发一致性

我们现在基本都是使用mysql来实现对金额的操作,保证数据的准确性,那能不能使用redis来对金额进行操作并保证数据的准确性呢?可以利用 redis 的事务来实现这个想法。

redis 的 WATCH 和 EXEC 可以提供类似事务的机制:WATCH观察key是否被改动,如果提交时key被改动,EXEC将返回null,表示事务失败。

假设redis客户端执行:

$money = GET key $money = $money - $diff SET key $money

在并发量大的时候可能会出现并发一致性问题,可以在redis客户端这样执行:

WATCH key $money = GET key $money = $money - $diff MULTI SET key $money EXEC

在 WATCH 之后,EXEC 执行之前,如果key的值发生变化,则EXEC会失败。redis的WATCH本质上使用的就是乐观锁CAS机制来保证事务性。

可能有的同学会有疑惑,Redis不是单线程运行的吗,为什么还需要事务来保证一致性呢?
Redis虽然是单线程运行命令,但是它可以拥有多个连接,Redis在接收各个连接发送的命令不是按块接收,意思是客户端发送给Redis的多个命令被接收时可能中间也会有其他客户端的命令,所以我们需要MULTI、EXEC命令来实现事务功能。
那又有同学可能会有疑惑,既然都实现事务功能了,为什么还需要 WATCH 命令来监视数据呢?
这个其实和上面说的原因也是一样的,Redis接收命令的顺序客户端是控制不了的,所以如果多个客户端同时发送一些包含在事务中的命令给服务端,Redis会按接收命令的顺序来执行这些事务命令,这样就有可能导致后面执行的客户端使用的不是自己想要的数据。所以我们使用WATCH 命令来监控数据的状态,如果在提交时数据被更改那么就会提交失败,这就是使用到乐观锁的地方。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值