乐观锁 mysql_mysql乐观锁解决并发问题

博客2:https://www.cnblogs.com/laoyeye/p/8097684.html

1、使用版本号实现乐观锁

版本号的实现方式有两种,一个是数据版本机制,一个是时间戳机制。具体如下。

下单操作包括3步骤:

1.查询出商品信息

select (status,status,version) from t_goods where id=#{id}

2.根据商品信息生成订单

3.修改商品status为2

update t_goods

set status=2,version=version+1

where id=#{id} and version=#{version};

2、使用条件限制实现乐观锁

UPDATE t_goods

SET num = num - #{buyNum}

WHERE

id = #{id}

AND num - #{buyNum} >= 0

AND STATUS = 1

问题引入

当事务的隔离级别是REPEATABLE_READ情况下:当前事务不能select到并发事务中已经提交的事务。

当事务的隔离级别是READ COMMITTED情况下:当前事务能select到并发事务中已经提交的事务。

Mysql默认的事务隔离级别为repeatable_read :https://www.cnblogs.com/kangshuai/p/5735374.html

读:在一个事物里面的select语句 不会受到其他事务(不管其他事务有没有commit)的影响。

写:对一条记录而言,一个事务一旦update一条记录,其他事务只能等待这个事务commit才能update那条记录。

乐观锁处理并发的原理 重点

1)一个事物中的select语句可能不会收到其他事物的影响,也就是可能查不到其他并发中未提交的事物(即使提交了 如果是REPEATABLE_READ也查不到)。所以两个事物共同执行时产生了并发的冲突。

2)虽然这个被并发的字段通过select查不出来,但是在where条件语句中 这个字段会受到其他事物的影响 。所以可以利用这点 可以读到并发事物影响的数据 ,从而做出判断,防止并发。

所以可用下面方式处理(利用乐观锁处理事物的并发)

数据库增加一个锁的处理列(版本号),查询的时候多查一个版本号, update的时候 where条件附加一个版本号条件并且更新时候并且把版本号+1,处理流程

1)select num,version from table;

2)update table set num=num-1 ,version =version+1 where condition=? version=#{version}

3)Query OK, 1 rows affected (0.04 sec) | 注意:1 rows affected

update的时候 where条件附加一个版本号条件并且更新时候并且把版本号+1: update table set num=num-1 ,version =version+1 where condition=? version=#{version}

如果出现了查询时候的版本号和where条件的版本号不一致 说明其他事物并发影响到了版本号 version,此时update语句的影响行数(Query OK, 1 rows affected (0.04 sec))是0 然后做异常处理。()

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值