数据库并发问题
文章目录
以下内容为在数据库并发中出现的各种问题。
脏读(dirty read)
A事务读到B事务刚修改的值,但是B事务撤销了,也A事务读到的值就是假的了。
时间 |
转账事务A |
取款事务B |
---|---|---|
T1 |
|
开始事务 |
T2 |
开始事务 |
|
T3 |
|
查询账户余额为1000元 |
T4 |
|
取出500元把余额改为500元 |
T5 |
查询账户余额为500元(脏读) |
|
T6 |
|
撤销事务余额恢复为1000元 |
T7 |
汇入100元把余额改为600元 |
|
T8 |
提交事务 |
|
不可重复读是指A事务读取了B事务已经提交的更改数据。假设A在取款事务的过程中,B往该账户转账100元,A两次读取账户的余额发生不一致:
时间 |
取款事务A |
转账事务B |
---|---|---|
T1 |
|
开始事务 |
T2 |
开始事务 |
|
T3 |
|
查询账户余额为1000元 |
T4 |
查询账户余额为1000元 |
|
T5 |
|
取出100元把余额改为900元 |
T6 |
|
提交事务 |
T7 |
查询账户余额为900元(和T4读取的不一致) |
|
幻象读与不可重复读的区分是,前者是新增时出现,后者是更改或删除出现。 A事务读取B事务提交的新增数据,这时A事务将出现幻象读的问题。幻象读一般发生在计算统计数据的事务中,举一个例子,假设银行系统在同一个事务中,两次统计存款账户的总金额,在两次统计过程中,刚好新增了一个存款账户,并存入100元,这时,两次统计的总金额将不一致:
时间 |
统计金额事务A |
转账事务B |
---|---|---|
T1 |
|
开始事务 |
T2 |
开始事务 |
|
T3 |
统计总存款数为10000元 |
|
T4 |
|
新增一个存款账户,存款为100元 |
T5 |
|
提交事务 |
T6 |
再次统计总存款数为10100元(幻象读) |
|
A事务撤销时,把已经提交的B事务的更新数据覆盖了。这种错误可能造成很严重的问题,通过下面的账户取款转账就可以看出来:
时间 |
取款事务A |
转账事务B |
---|---|---|
T1 |
开始事务 |
|
T2 |
|
开始事务 |
T3 |
查询账户余额为1000元 |
|
T4 |
|
查询账户余额为1000元 |
T5 |
|
汇入100元把余额改为1100元 |
T6 |
|
提交事务 |
T7 |
取出100元把余额改为900元 |
|
T8 |
撤销事务 |
|
T9 |
余额恢复为1000元(丢失更新) |
|
A事务覆盖B事务已经提交的数据,造成B事务所做操作丢失:
时间 |
转账事务A |
取款事务B |
---|---|---|
T1 |
|
开始事务 |
T2 |
开始事务 |
|
T3 |
|
查询账户余额为1000元 |
T4 |
查询账户余额为1000元 |
|
T5 |
|
取出100元把余额改为900元 |
T6 |
|
提交事务 |
T7 |
汇入100元 |
|
T8 |
提交事务 |
|
T9 |
把余额改为1100元(丢失更新) |
|
文章作者 fatkun
上次更新 2010-12-26