mysql中 for update 使用

forupdate用于在数据库中上锁,确保事务中对特定行的排它访问,防止并发写入冲突。当一个事务对某行使用forupdate时,其他事务只能读取此行,不能进行更新操作,直至当前事务结束。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

for update是在数据库中上锁用的,可以为数据库中的行上一个排它锁。当一个事务的操作未完成时候,其他事务可以读取但是不能写入或更新。

例子:
比如一张表三个字段 , id(商品id), name(商品名字) , count(数量) 
当商品抢购时候会显示剩余商品件数,如果并发量大的时候,商品自减的值可能不准确。所以当我们在一个事务中对count字段进行修改的时候,其他事务应该只能读取指定id的count,而不能进行update等操作。这个时候就需要用到for update.

sql语句:
start transaction ; 
select * from table_name where id =1 for update ;

update table_name set count = count - 1 where id= 1;

此时如果另一个事务也想执行类似的操作:
start transaction ; 
select * from table_name where id =1 for update ; 
//下面的这行sql会等待,直到上面的事务回滚或者commit才得到执行。 
update table_name set count = count - 1 where id= 1;

注:当选中某一个行的时候,如果是通过主键id选中的。那么这个时候是行级锁。 
其他的行还是可以直接insert 或者update的。如果是通过其他的方式选中行,或者选中的条件不明确包含主键。这个时候会锁表。其他的事务对该表的任意一行记录都无法进行插入或者更新操作。只能读取。

那是一种行级锁,一旦用户对某个行施加了行级加锁,则该用户可以查询也可以更新被加锁的数据行,其它用户只能查询但不能更新被加锁的数据行.如果其它用户想更新该表中的数据行,则也必须对该表施加行级锁.即使多个用户对一个表均使用了共享更新,但也不允许两个事务同时对一个表进行更新,真正对表进行更新时,是以独占方式锁表,一直到提交或复原该事务为止。行锁永远是独占方式锁。
只有当出现如下之一的条件,便释放共享更新锁:
(1)、执行提交(COMMIT)语句;
(2)、退出数据库(LOG OFF)

(3)、程序停止运行。

那么,什么时候需要使用for update?就是那些需要业务层面数据独占时,可以考虑使用for update。场景上,比如火车票订票,在屏幕上显示邮票,而真正进行出票时,需要重新确定一下这个数据没有被其他客户端修改。所以,在这个确认过程中,可以使用for update。这是统一的解决方案方案问题,需要前期有所准备
————————————————
版权声明:本文为优快云博主「飞起的人生」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.youkuaiyun.com/qq_35349114/article/details/84027745

### MySQLFOR UPDATE 锁机制 `FOR UPDATE` 是 MySQL 提供的一种行级锁定机制,用于在事务中确保数据一致性。当在一个事务中执行 `SELECT ... FOR UPDATE` 查询时,所选中的行会被加上排他锁(exclusive lock),这意味着其他事务无法修改这些被锁定的行,直到当前事务完成并释放锁。 #### 行级锁 vs 表级锁 - 如果查询条件中涉及索引列(尤其是主键或唯一索引),MySQL 通常只会对符合条件的具体行加锁,这种行为称为 **行级锁**[^1]。 - 若查询条件未命中任何索引,则可能导致整个表被锁定,即发生 **表级锁**[^2]。 #### 加锁过程与并发控制 一旦某一行通过 `FOR UPDATE` 被锁定,在另一个事务尝试对该同一行也发起 `FOR UPDATE` 请求时,后者将进入等待状态直至前一事务结束(提交或回滚)。然而需要注意的是,普通的只读型 SELECT 不受影响——即使目标记录已被另一事务以 `FOR UPDATE` 方式锁定,新来的只读请求仍可顺利完成而不需排队等候解锁[^4]。 以下是关于如何运用此功能的一些具体例子: ```sql START TRANSACTION; -- 假设我们想要更新订单号为1的状态之前先确认其现状 SELECT * FROM orders WHERE order_id = 1 FOR UPDATE; UPDATE orders SET status='shipped' WHERE order_id=1; COMMIT; ``` 上述脚本展示了典型的使用模式:启动一个新的显式事务;接着利用带 `FOR UPDATE` 子句的选择命令获取特定条目的最新版本及其上的写权限;最后做出必要的更改再提交变更。 ### 使用场景分析 考虑到性能开销以及潜在死锁风险等因素,合理规划何时何地应用此类强约束显得尤为重要。下面列举了几种适合采用 `FOR UPDATE` 的典型情境: 1. 当应用程序需要基于现有数据库内容计算得出新的数值后再存入DBMS里头的时候; 2. 需要防止两个独立进程同时访问相同的数据集从而引发竞争状况的情形下; 3. 实现队列管理或者库存控制系统之类的功能模块期间。 尽管如此,过度依赖于这类悲观策略也可能带来负面影响比如降低吞吐量等负面效应因此应当谨慎权衡利弊之后决定是否采纳该方法论作为解决方案的一部分[^3]. 相关问题
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值