单台tomcat下,由于是多线程,mysql会存在多个连接,如果不做处理,会产生多线程数据不安全问题,此时可在具体的service中加锁即可处理
多台tomcat下,就要使用分布式锁
mysql 某一个 操作(insert,update,delete)是原子性的,不需要加锁,但是如果存在 ABA 问题的情况下,必须要加锁。
ABA问题 :
select num from goods
if num > 0
update good set num=num-1
那么此时就不是原子操作,就要使用分布式锁
分布式锁的常见方式
1、数据库的乐观锁( 加版本号)
select version ,num from goods where local_version = version
if num > 0
update good set num=num-1 ,version=version+1 where version = local_version
2、悲观锁(一锁二查三更新) select for update(mysql默认情况下使用表锁,使用索引情况下会使用行锁)
针对事务,必须在事务中使用
这里需要注意的一点是不同的数据库对select for update的实现和支持都是有所区别的,例如oracle支持 select for update no wait,表示如果拿不到锁立刻报错,而不是等待,mysql就没有no wait这个选项。另外mysql还有个问题是select for update语句执 行中所有扫描过的行都会被锁上,这一点很容易造成问题。因此如果在mysql中用悲观锁务必要确定走了索引,而不是全表扫描。
3、redis
后期更新
4、zookeeper
后期更新
最后 由于春运快到了,给大家安利一个抢火车票的小程序心到抢票,微信扫码关注点击立即抢票即可
个人亲测效率很高,大家也可以加他们官方微信 xdticket 咨询。