mysql 脏读解析

脏读(Dirty Read) 是指一个事务读取了另一个事务尚未提交的修改数据。如果该修改最终被回滚,那么读取到的数据就是无效的“脏数据”

脏读只会发生在隔离级别为 READ-UNCOMMITTED(读未提交) 时。MySQL默认隔离级别为 REPEATABLE-READ,可以避免脏读。

 

示例:

-- 创建账户表
CREATE TABLE `account` (
  `id` int(2) NOT NULL AUTO_INCREMENT,
  `name` varchar(10) DEFAULT NULL,
  `balance` int(3) DEFAULT '0',
  PRIMARY KEY (`id`)
) ENGINE=InnoDB;


-- 插入一条数据,用户A的账户余额为1000元
INSERT INTO `account` (`id`, `name`, `balance`) VALUES (1, 'A', 1000);

 

image

image

 

对应的危害:

  1. 数据不一致:事务B在T2时读到的余额是900,并可能基于这个错误数据进行了后续业务操作(如计算、扣款等)。
  2. 决策基于无效数据:随后事务A在T3时回滚,意味着“余额为900”这个状态从未真正存在过。事务B的所有操作都建立在一个虚假的数据快照上,这可能导致严重的数据逻辑错误。

 

何如避免:

  将事务隔离级别设置为 READ-COMMITTED 或更高,即可有效避免脏读。

  在 READ-COMMITTED 级别下,一个事务只能读取到其他事务已经提交的数据。如果在上述示例的T2时刻,会话B查询用户A的余额,它将读取到原始的 1000,而不是会话A未提交的修改,从而保证了数据的一致性。

 

 

posted @ 2023-06-21 10:17  方达达  阅读(3)  评论(0)    收藏  举报