我们都知道计算机的处理速度是非常快的,但是再快的计算机也面临这样的问题,有很多请求在同时所有操作必须在同一个资源上执行。因此,在数据库中,引入了事务来解决此类问题。让我们举一个简单的例子。在街上买了2排Yakult,让支付宝转了25元给商家。这个时候,我会这样做。支付宝先查看我的余额是否还有25元,然后从我的余额中扣除25元,然后商家的支付宝就会增加25元。如果我的支付宝只有25元,在转账给商家的那一刻,我用另一部手机在拼多多上买了一个20元的西瓜,也是用支付宝支付。因为数据库事务,这两个操作是不一样的。不会同时成功。Mysql数据库有4个特点,我们称之为ACID。即原子性、一致性、隔离性和持久性。原子性(atomicity)一个事务必须被看作是一个不可分割的最小工作单元。整个事务中的所有操作,要么全部提交成功,要么全部失败回滚。对于一个事务来说,不可能只执行一部分操作,这就是事务的原子性。上面的例子,要么我扣了25元,养乐多商家多收了25元,要么我没扣钱,商家也没收多少。不会出现我的钱被扣,商家收不到钱的情况。估计每天都有各种抱怨和纠纷。一致性(consistency)数据库总是从一种一致状态转换到另一种一致状态。(在前面的例子中,一致性保证了这25元要么不是我给商家的,要么已经到商家的账户里了,不会出现25元凭空消失的情况。)隔离(隔离)通常来自于,即一个事务所做的更改在最终提交之前对其他事务不可见。(前面的例子,我还在食堂给卖家付25元的时候,我在拼多多的另一笔支付交易,我感觉我还有25元。只有我提交了整笔交易后,另一笔交易才知道我已经扣除了相应的金额。因此,我们在进行扣除的时候,还需要判断余额是否足够。)持久性(durability)一旦事务被提交,所做的更改将永久保存到数据库中。(即使此时系统崩溃,修改的数据也不会丢失。)在实时中,如果数据库严格遵循这个属性,势必会降低数据库的性能。因此,在InnoDB中,有许多不同的事务级别。它们是未提交读、提交读、可重复读和序列化。Readuncommitted:别人改了数据的事务还没有提交,我在自己的事务中可以读到。在上面的例子中,如果拼多多的扣款发生在我的金额减了25之后,但是交易还没有提交,这个时候我去读数据库的时候,已经读到数据为0了。显然,如果这个时候,之前的时间被回滚了,那么这次读的结果就叫做脏读。ReadCommitted:别人改数据的事务已经提交,我只能在自己的事务中读取。在上面的例子中,如果25的事务扣除没有完成,那么结果25全部读取。如果在后续事务中多次读取余额,那么有可能读到25或者0,我们称之为不可重复读。可重复读:别人改数据的事务已经提交,我的事务中不会读。第一次读取数据时,实际上形成了对应的视图,后面只能读取对应的数据。Serial:我的交易还没有提交,所以其他人不能更改数据。这是严格序列化的。在上面的例子中,只有前面的25元扣完之后,才能开始后面的交易。对于这四个隔离级别,并行性能依次降低,安全性依次提高。好了,今天我们简单介绍下mysql的事务。不知道对你有没有启发。欢迎大家关注我,一起学习,一起进步。
