事务并发三大问题

脏读 不可重复读 幻读 都是读一致性问题

1 脏读

当一个事务对数据进行修改,那修改还没有提交,但是另外一个事务访问了这个数据,但是这个数据并没有提交到数据库,读到了“脏数据”!!!

事务a

select * from account where id = 13

事务b

update account set age = 18 where id = 13

事务a

select * from account where 13

----》age = 18

2 不可重复读(update,delete)

在一个事务内多次读同一数据,在第一个事务两次读时间之中,第二个事务中途修改导致,第一个事务读第一次和第二次的数据不太一样,这就是不可重复读。重复读的时候数据不一样,不知道取哪个,总有一个数据是错的。

事务a

select * from account where id = 13;

事务b

update account set age = 18 where id = 13;

commit;

事务a

select * from account where 13;

----》age = 18

3 幻读(insert)

在第一个事务访问数据两次,中途第二个事务来添加一条数据或者删除一条数据,造成第一次看有这条数据,第二次看没有这条数据。或者第一次看没有这条数据,第二次看有这条数据。

事务a

select * from account where age>18;

事务b

insert into account values(555,‘xiaojihe’,20);

commit;

事务a

select * from account where age>18;

----->多个一条数据

针对事务并发的问题,有一个SQL92 ANSI/ISO标准

隔离级别越低,事务请求的锁越少,效率越高,安全性越低。

Read Uncommitted(未提交读):最低隔离级别,脏读、不可重复读、幻读都会导致。

Read Committed(已提交读):解决脏读。(大部分数据库系统)

Repeatable(可重复读):解决脏读、不可重复读。(InnoDB默认使用)

Serializable(串行化):解决并发事务所有问题,不建议用,效率低。最高的隔离级别,完全服务ACID的隔离级别。

ACID:原子性、一致性、隔离性、永久性