乐观锁( Optimistic Locking ) 相对悲观锁而言,乐观锁假设认为数据一般情况下不会造成冲突,所以在数据进行提交更新的时候,才会正式对数据的冲突与否进行检测,如果发现冲突了,则让返回用户错误的信息,让用户决定如何去做。
Redis Watch 命令用于监视一个(或多个) key ,如果在事务执行之前这个(或这些) key 被其他命令所改动,那么事务将被打断
Redis Unwatch 命令用于取消 WATCH 命令对所有 key 的监视。
无冲突执行成功
127.0.0.1:6379> WATCH money
OK
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> DECRBY money 10
QUEUED
127.0.0.1:6379(TX)> EXEC
1) (integer) 90
================================== //事务,未执行
127.0.0.1:6379> WATCH money
OK
127.0.0.1:6379> MULTI
OK
127.0.0.1:6379(TX)> DECRBY money 90
QUEUED
================================= 客户端2修改
127.0.0.1:6379> get money
"90"
127.0.0.1:6379> DECRBY money 40
(integer) 50
127.0.0.1:6379>
================================= 回到客户端1,执行事务失败
127.0.0.1:6379(TX)> exec
(nil)
127.0.0.1:6379> get money
"50"
应用场景
(乐观锁主要用于抢红包,淘宝抢购,秒杀之类的并发操作)
在限量秒杀抢购的场景,一定会遇到抢购成功数超过限量的问题和高并发的情况影响系统性能
1、虽然能用数据库的锁避免,超过限量的问题。但是在大并发的情况下,大大影响数据库性能
2、为了避免并发操作数据库,我们可以使用队列来限制,但是并发量会让队列内存瞬间升高
3、我们又可以用悲观锁来实现,但是这样会造成用户等待,响应慢体验不好