SQL Server中计数器递增操作后事务回滚行为咨询
事务回滚后attendeeCount字段的取值规则
核心结论
回滚会直接将attendeeCount重置为本次事务开始前的原始值,不会基于其他操作修改后的最新值做递减。
具体原因
- 所有支持ACID特性的主流关系型数据库(SQL Server、MySQL、PostgreSQL等)的事务回滚逻辑,都依赖事务启动时记录的undo日志/数据快照实现。你执行
SET attendeeCount = attendeeCount + @incrementBy的修改操作时,数据库会先把attendeeCount修改前的原始值写入undo日志,回滚时直接用该原始值覆盖当前字段值即可,不会做额外的递减计算。 - 不存在“其他操作已修改该字段最新值”的前提:当你在事务中执行UPDATE语句时,数据库会自动给对应数据行加行锁,锁会持续到当前事务提交或回滚完成。在此期间其他事务无法修改该行的
attendeeCount值,自然也不会出现需要基于其他事务修改后的值做回滚计算的情况。
简易验证逻辑
你可以通过本地测试快速验证该规则:
- 初始化测试行的
attendeeCount值为10 - 开启事务A,执行
UPDATE 表名 SET attendeeCount = attendeeCount + 3 WHERE 过滤条件,事务A内查询可见attendeeCount变为13 - 新开事务B,尝试修改同一行的
attendeeCount,会直接进入阻塞状态 - 回滚事务A,查询可得
attendeeCount回到初始值10,同时事务B的阻塞自动解除
内容的提问来源于stack exchange,提问作者Andy Ewer
相关产品推荐
相关产品推荐

