数据库事务的四大特性
原子性
事务包含的所有操作要么成功,要么失败回滚
一致性
事务必须是数据库从一个一致性状态到另一个一致性状态。
事务执行之前和之后必须都是一致性的一个状态
隔离性
当多个用户并发访问数据库,比如同一张表时,数据库为每一个用户开启的事务,
不会被其他事务的操作干扰,多个并发事务之间要相互隔离
持久性
事务一旦被提交,那么数据库的数据改变是永久性的,即便是数据库遇到故障的时候也不会丢失事务操作。
数据库事务的隔离级别
数据库有4中事务隔离级别,分别从低到搞为:
Read uncommitted(读,未提交)
Read committed(读,已提交)
Repetablead(可重复读)
Serializable(序列化又名串行化)
读、未提交(Read uncommitted)
一个事务可以读取到另一个未提交事务的数据
解决--脏读
例:a转给b 500元,a已经下发,但是没有提交,此时b可以查看到到了500,a由于未提交事务,此时测回,可导致a已经见到500到账,但是又没有了。
此时就可使用Read committed(读、已提交)解决数据脏读问题。
读、已提交(Read committed)
事务要等待另一个事务提交后才能读取数据。
解决--不可重复读
例:a事务要进行扣款(之前已经读取过数据),但是b事务正在处理中,需要等待b事务进行处理完成,直到b事务处理完成之后,b事务结束,此时a事务才能重新继续处理,然而此时就需要重读数据,导致数据不正确。
读提交的时候,需要等到其他update操作完成才能读取数据,可以解决脏读问题,
但是这里一个事务范围内两个相同的查询返回了不同的数据,这个就是不可重复读。
重复读(Repeatable read)
重复读,就是在开始读取数据(事务开启)时,就不再允许修改操作,MySQL是这一级别的。
解决--重复读
a事务进行扣款(开启重复读事务),此时b事务就无法对数据进行处理,需要等待a事务处理完成之后再次进行数据处理。
重复读可以解决不可重复读的问题,其实不可重复读就是针对update操作的。
但是可能会出现幻读问题,**幻读**是针对insert操作。
什么是幻读?
是a事务在开启了重复读的时候,b插入了一条数据,此时可能会出现数据幻读。因为重复读只针对update操作,幻读是针对insert操作。
序列化(Serializable)
解决幻读
序列化时最高的事务隔离级别,在该级别下,事务串行顺序执行,可以避免脏读、不可重复读、幻读。
但是这种事务隔离级别效率底下,比较消耗数据库性能。
数据库默认的事务
大多数数据库的事务隔离级别是Read committed
数据库 | 默认事务级别 |
Sql Server | Read committed(读、已提交) |
Oracle | Read committed(读、已提交) |
MySQL | Repeatable(可重复读) |