事务
1、定义:所有操作必须成功完成,否则在每个操作中所作的所有更改都会备撤销。
2、事务的ACID
原子性atomicity 一致性consistency 隔离性isolation 持续性durability
2-1、原子性: 事务是数据库的逻辑工作单位,事务中包含的各操作要么都做,要么都不做
2-2、一致性: 事务执行的结果必须是数据库从一个一致性状态变到另一个一致性状态。因此当数据库只包含成功事务提交的结果时,
就说明数据库处于一致性状态。
2-3、隔离性: 一个事务的执行不能被其他事务干扰。
2-4、持续性: 即永久性,一个事务一旦提交,它对数据库中数据的改变就应该是永久行的。
3、MySQL的四中隔离级别
3-1、read uncommitted(读取未提交的内)
所有事务都可以看到其他未提交事务的执行结果。 也称之为脏读,很少应用与实际
3-2、read committed(读取提交内容)
一个事务只能看见已提交事务所做的改变。
3-3、repeatable read(可重复读)
MySQL默认事务隔离级别,确保同一事务的多个实例在并发读取数据时,会看到同样的数据行。不过,会导致幻读。
幻读指用户读取某一范围数据行时,另一个事务又在该范围内插入了新行。当用户再读取该范围的数据行时,会发现出现新的幻影行
3-4、serializable(可串行化)
在每个读的数据行上加上共享锁。这个级别可能导致大量的超时现象和锁竞争。
4、事务隔离的原理
1、一次*or两段锁
在大量并发访问时候,为了预防死锁,一般应用中推荐使用一次*法,就是在方法的开始阶段,已经预先知道会用到哪些数据,
然后全部锁住,在方法运行之后,在全部解锁。但这种方式不适用于数据库,因为数据库不知道会用到哪些数据。
数据库采用的是两段锁协议,将事务分成两个阶段,加锁阶段和解锁阶段。
加锁阶段: 在对任何数据进行读操作之前要申请并获得S锁(共享锁,其他事务可以继续加共享锁,但不能加排它锁),在进行写
操作之前要申请X锁(排它锁,其他事务不能再获得任何锁)。如果加锁不成功的话,则事务进入等待状态,直到加锁成功才能继续执行。
解锁阶段: 当事务释放了一个*以后,事务进入解锁阶段,在该阶段只能进行解锁操作不能再解析加锁操作。
不可重复读与幻读的区别:
不可重复读重点在于update和delete,而幻读在于insert
5、mvcc在MySQL的innodb实现
在innodb中,会在每行数据后添加两个额外的隐藏的值来实现MVCC,这两个值一个记录这行数据何时被创建,另一个记录这行
数据何时过期(或者被删除)在实际操作中,存储的并不是时间,而是事务的版本号,每开启一个新事务,事务的版本号就会
递增。在可重复读的事务隔离级别下:
select时,读取创建版本号不大于当前事务版本好,删除版本号为空或大于当前事务版本号
insert时,保持当前事务版本号为行的创建版本号
delete时,保持当前版本号为行的删除版本号
update时,插入一条新记录,保存当前事务版本号为行创建的版本号,同时保持当前事务版本号到原来删除的行