一、什么是事务?
事务(Transaction),就是将一组SQL语句放在同一批次内去执行,如果一个SQL语句出错,则该批次内 的所有SQL都将被取消执行。
二、事务的特点和限制
特点: 一个事务中如果有一个数据库操作失败,那么整个 事务的所有数据库操作都会失败,数据库数据就会 回滚到该事务开始之前的状态。
限制:MySQL数据库中仅InnoDB和BDB类型的数据库表 支持事务。
三、事务的ACID原则
原子性(Atomic):意味着数据库中的事务执行是作为原子粒度。即不可再分,整个语句要么执行,要么不执行。
一致性(Consist):即在事务开始之前和事务结束以后,数据库的完整性约束没有被破坏。
隔离性(Isolated):事务的执行是互不干扰的,一个事务不可能看到其他事务运时,中间某一时刻的数据。
持久性(Durable):意味着在事务完成以后 ,该事务所对数据库所作的更改便持久的保存在数据库之中,并不会被回滚。
四、mysql实现事务的步骤
1、关闭mysql自动提交 set autocommit = 0;
2、开启一个事务,标记事务的起始点 start transaction;
3-1、向数据库提交事务 commit;
3-2、将事务回滚,所有的数据库操作被取消 rollback;
4、开启mysql自动提交 set autocommit = 1;
注意:*3-1和3-2不能同时执行,选一个执行。
# 事务
-- 新建bank表
create table bank(
bid int primary key auto_increment,
bname varchar(10),
bmoney decimal(20,2)
);
-- 添加数据
insert into bank(bname,bmoney)
values('张三',5),('李四',1000);
-- 关闭MySQL自动提交
set autocommit = 0;
-- 开启一个事务,标记事务的起始点
start transaction;
-- 一组sql语句
update bank set bmoney = bmoney - 100
where bname = '李四';
update bank set bmoney = bmoney + 100
where bname = '张三';
-- 事务的结束(提交或回滚)
commit; -- 向数据库提交事务
rollback; -- 将事务回滚,所有的数据库操作被取消
-- 开启MySQL自动提交
set autocommit = 1;
五、什么是事务的隔离性?
为了让不同的事务之间相互不存在干扰,就需要对事务的操作进行隔离,事务的隔离性也就是将操作同一个数据的事务相互分离,让操作之间分开有序的执行。
六、用什么方法实现事务的隔离性
通常数据库里都是采用锁的机制,保证事务之间的隔离性。
七、mysql中的锁
锁分类:
基于锁的属性分类:共享锁(读锁、S锁)、排他锁(写锁,X锁)。
基于锁的粒度分类:表锁、行锁(记录锁、间隙锁、临键锁)。
基于锁的状态分类:意向共享锁、意向排他锁。
八、事务的隔离级别
事务并发问题:在事务并发执行的时候,如果不进行事务隔离,那么就会产生脏写、脏读、不可重复读、幻读的问题。
事务的隔离级别:
1. READ_UNCOMMITTED 读未提交
2. READ_COMMITTED 读提交(不可重复读)
3. REPEATABLE_READ 可重复读
4. SERIALIZABLE 串行化
每个隔离级别都针对事务并发问题中的一种或几种进行解决,事务级别越高,解决的并发事务问题也就越多,同时也意味着加的锁就越多,所以性能也会越差。
九、事务的隔离级别解决的问题
1. READ_UNCOMMITTED
事务读取:不加锁。
事务写入:加写锁。
解决问题:脏写。
存在问题:脏读、不可重复读、幻读。
2. READ_COMMITTED
事务读取:加读锁(每次select完成都会释放读锁)。
事务写入:加写锁。
解决问题:脏写、脏读。
存在问题:不可重复读、幻读。
3. REPEATABLE_READ
事务读取:加读锁(每次select完不会释放锁,而是事务结束后才释放)(如果是mysql的innodb还会加间隙锁)。
事务写入:加写锁。
解决问题:脏写、脏读、不可重复读、幻读(如果是mysql的innodb则已解决)。
存在问题:幻读(如果是mysql的innodb则已解决)。
4. SERIALIZABLE
不管读取还是修改所有的事务串行化执行,一个事务的执行必须等其他事务结束。