注册 登录  
 加关注
   显示下一条  |  关闭
温馨提示!由于新浪微博认证机制调整,您的新浪微博帐号绑定已过期,请重新绑定!立即重新绑定新浪微博》  |  关闭

PostgreSQL 中文网

 
 
 

日志

 
 

PostgreSQL: Transaction Isolation  

2011-06-29 10:43:31|  分类: Postgres基础 |  标签: |举报 |字号 订阅

  下载LOFTER 我的照片书  |

   
        数据库的隔离级别有四种,分别是 Read uncommitted ,Read committed Repeatable read,Serializable ,
PostgreSQL 数据库的默认事务隔离级别是 Read committed , 有系统参数可以更改数据库隔离级别。事务隔离
级别的特点需要根据以下三种现象来判定:


--1 事务隔离级别的三种现象
A: 脏读 ( dirty read )
     脏读就是指当一个事务正在访问数据,并且对数据进行了修改,而这种修改还没有提交到数据库中,这时,
另外一个事务也访问这个数据,然后使用了这个数据。因为这个数据是还没有提交的数据,那么另外一个事务读
到的这个数据是脏数据,依据脏数据所做的操作可能是不正确的,简单的说,脏读即读到未提交的数据。

B: 不可重复读 ( nonrepeatable read )
      不可重复读是指在一个事务内,多次读同一数据。在这个事务还没有结束时,另外一个事务也访问该同一数据。
那么,在第一个事务中的两次读数据之间,由于第二个事务的修改,那么第一个事务两次读到的数据可能是不一样的。
这样就发生了在一个事务内两次读到的数据是不一样的,因此称为是不可重复读。简单地说,不可重复读即指在一个
事务中读到数据不一样,原因是其它会话已经更改了并提交了这些数据。

C: 三幻影读 (phantom read )
       幻觉读是指当事务不是独立执行时发生的一种现象,例如 第一个事务对一个表中的数据进行了修改,这种修
改涉及到表中的全部数据行。同时,第二个事务也修改这个表中的数据,这种修改是向表中插入一行新数据。那么,
以后就会发生操作第一个事务的用户发现表中还有没有修改的数据行,就好象发生了幻觉一样。


--2 Transaction Isolation Levels

Isolation Level Dirty Read Nonrepeatable Read Phantom Read
Read uncommitted Possible Possible Possible
Read committed Not possible Possible Possible
Repeatable read Not possible Not possible Possible
Serializable Not possible Not possible Not possible


                                              图一: SQL Transaction Isolation Levels

   备注:红色部分将在下面部分做实验验证。


--3 事务隔离级别参数
default_transaction_isolation (enum)
       Each SQL transaction has an isolation level, which can be either “read uncommitted”, “read committed”, “repeatable read”, or “serializable”. This parameter controls the default isolation level of each new transaction. The default is “read committed”.

--3.1查看当前事务隔离级别
skytf=> show default_transaction_isolation;
 default_transaction_isolation
-------------------------------
 read committed
(1 row)


--4 "Read committed ISOLATION LEVEL" 举例
     "Read committed"是 PostgreSQL 的默认事务隔离级别, 根据图一,"Read committed"可能发生不可重复读
(Nonrepeatable Read), 下面验证一下。


--4.1 一张测试表
skytf=> select * from test_41;
 id | name
----+------
  2 | b
  3 | c
  1 | a
(3 rows)


--4.2 事务一
skytf=> begin
skytf=> select * from test_41 where id=1;
 id | name
----+------
  1 | a
(1 row)

--4.3 事务二:修改这行数据
skytf=> update test_41 set name='aaa' where id=1;
UPDATE 1
   
--4.4 再回到事务一
skytf=> select * from test_41 where id=1;
 id | name
----+------
  1 | aaa
(1 row)

      备注:发现在事务一中,两次读到的数据不一样了(红色部分),这就是不可重复读。

 

--5 "REPEATABLE READ READISOLATION LEVEL" 举例
    根据图一,"REPEATABLE READ " 将不会出现“不可重复读”,下面通过实验验证一下;


--5.1 表数据
skytf=> select * From test_41;
 id | name
----+------
  2 | b
  3 | c
  1 | aaa
(3 rows)

--5.2 事务一
skytf=> begin;
BEGIN
skytf=> SET TRANSACTION  ISOLATION LEVEL  REPEATABLE READ ;
SET
skytf=> select * from test_41 where id=2;
 id | name
----+------
  2 | b
(1 row)

--5.3 事务二:修改这行数据
skytf=> update test_41 set name='bbb' where id=2;
UPDATE 1

--5.4 再回到事务一
skytf=> select * from test_41 where id=2;
 id | name
----+------
  2 | b
(1 row)

     备注: 将 PostgreSQL 事务隔离级别设置成 " REPEATABLE READ" 后, "不可重复读"将不再出现。
              另外:这里是在会话中更改事务的隔离级别,只对当前会话有效,如果修改配置文件是的
              default_transaction_isolation 参数,则会影响全局。   

--6  附: 事务隔离级别设置语法
Name
     SET TRANSACTION — set the characteristics of the current transaction

Synopsis
SET TRANSACTION transaction_mode [, ...]
SET SESSION CHARACTERISTICS AS TRANSACTION transaction_mode [, ...]

where transaction_mode is one of:

    ISOLATION LEVEL { SERIALIZABLE | REPEATABLE READ | READ COMMITTED | READ UNCOMMITTED }
    READ WRITE | READ ONLY

 

--7 总结
     今天主要测试了下 "Read committed " ,"Repeatable read " 事务隔离级别下的"Nonrepeatable Read "
特性,有兴趣的朋友可以去测试图二中的其它属性。 

  评论这张
 
阅读(27988)| 评论(0)
推荐 转载

历史上的今天

在LOFTER的更多文章

评论

<#--最新日志,群博日志--> <#--推荐日志--> <#--引用记录--> <#--博主推荐--> <#--随机阅读--> <#--首页推荐--> <#--历史上的今天--> <#--被推荐日志--> <#--上一篇,下一篇--> <#-- 热度 --> <#-- 网易新闻广告 --> <#--右边模块结构--> <#--评论模块结构--> <#--引用模块结构--> <#--博主发起的投票-->
 
 
 
 
 
 
 
 
 
 
 
 
 
 

页脚

网易公司版权所有 ©1997-2016