可重复读的问题

wh62592855 2009-04-28 05:51:16
今天看书看到孤立性等级的时候有四个等级:序列化 可重复读 提交的读 未提交的读
其中的可重复读有说到这样一种情况“虚拟读”或“虚拟插入”,其中有这样一段话是这样的
可重复读和序列化孤立级很相似,可它有一个很重要的不同点:虽然一个事务不能看到其他正在执行的当前事务做出的变化,但是它可以看到新的记录(其他事务添加到数据库的)。这有时被称作虚拟读或者虚拟插入,因为只在事务用过INSERT语句向数据库插入一个新纪录时它才发生。当执行一个SELECT查询是,其他同一时间正在进行的事务将会突然看到这个新的虚幻的行。

可我进行了一下试验,发现好像并不是这样的。
我打开了两个事务,假设为A和B,分别设置其事务孤立级为REPEATABLE READ。 完了在A事务中输入start transaction,接着向表test中INSERT一条新的记录,可是此时在B事务中对表TEST进行SELECT并不能看到新加入的数据,只有在A事务中COMMIT以后,在B事务中SELECT才可以看到新插入的记录。

请教一下是我对可重复读这种孤立级的理解有问题还是我测试的方法有问题?谢谢
...全文
376 11 打赏 收藏 转发到动态 举报
AI 作业
写回复
用AI写文章
11 条回复
切换为时间正序
请发表友善的回复…
发表回复
wh62592855 2009-04-29
  • 打赏
  • 举报
回复
呵呵 好吧 不管怎么样还是谢谢你的回答
如果将来需要用的到MYSQL我再深入的学好了
trainee 2009-04-29
  • 打赏
  • 举报
回复
[Quote=引用楼主 wh62592855 的帖子:]
我打开了两个事务,假设为A和B,分别设置其事务孤立级为REPEATABLE READ。 完了在A事务中输入start transaction,接着向表test中INSERT一条新的记录,可是此时在B事务中对表TEST进行SELECT并不能看到新加入的数据,只有在 A事务中COMMIT以后,在B事务中SELECT才可以看到新插入的记录。
[/Quote]

假如A还没commit, 就可以看到, 那就是read_uncommit了

ACMAIN_CHM 2009-04-29
  • 打赏
  • 举报
回复

这个东西比较难懂。我上上周末花了两天看了一遍中文版的MySQL文档。现在还是看英文的算了。中文翻得比较难懂。
wh62592855 2009-04-29
  • 打赏
  • 举报
回复
呵呵 这个官方的解释还涉及到了很多类型的锁啊
以前我在看ORACLE文档的时候就被搞得头昏昏的

我最近看的是本叫《MYSQL完全手册》的书
有些英文翻成中文也比较晦涩难理解
ACMAIN_CHM 2009-04-29
  • 打赏
  • 举报
回复

下面是官方文档的说明。看了也是一头雾水。

http://dev.mysql.com/doc/refman/5.1/zh/storage-engines.html#innodb-transaction-isolation

InnoDB中每个隔离级别的详细描述如下:

· READ UNCOMMITTED

SELECT语句以非锁定方式被执行,但是一个可能更早期版本的记录会被用到。因此,使用这个隔离级别,比如,读是不连贯的。着也被称为“脏读”(dirty read)。另外,这个隔离级别象READ COMMITTED一样作用。

· READ COMMITTED

一个有些象Oracle的隔离级别。所有SELECT ... FOR UPDATE和SELECT ... LOCK IN SHARE MOD语句仅锁定索引记录,而不锁定记录前的间隙,因而允许随意紧挨着已锁定的记录插入新记录。UPDATE和DELETE语句使用一个带唯一搜索条件的唯一的索引仅锁定找到的索引记录,而不包括记录前的间隙。在范围类型UPDATE和DELETE语句,InnoDB必须对范围覆盖的间隙设置next-key锁定或间隙锁定以及其它用户做的块插入。这是很必要的,因为要让MySQL复制和恢复起作用,“幽灵行”必须被阻止掉。

持续读行为如同在Oracle中:即使在同一事务内, 每个持续读设置并读取它自己的新快照。请参阅15.2.10.4节,“持续非锁定读”。

· REPEATABLE READ

这是InnoDB的默认隔离级别。带唯一搜索条件使用唯一索引的SELECT ... FOR UPDATE, SELECT ... LOCK IN SHARE MODE, UPDATE 和DELETE语句只锁定找到的索引记录,而不锁定记录前的间隙。用其它搜索条件,这些操作采用next-key锁定,用next-key锁定或者间隙锁定锁住搜索的索引范围,并且阻止其它用户的新插入。

在持续读中,有一个与之前隔离级别重要的差别:在这个级别,在同一事务内所有持续读读取由第一次读所确定的同一快照。这个惯例意味着如果你在同一事务内发出数个无格式SELECT语句,这些SELECT语句对相互之间也是持续的,请参阅15.2.10.4节,“持续非锁定读”。

· SERIALIZABLE

这个级别类似REPEATABLE READ,但是所有无格式SELECT语句被隐式转换成SELECT ... LOCK IN SHARE MODE。
wh62592855 2009-04-29
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 ACMAIN_CHM 的回复:]
MySQL的isolate级别一直是个头痛的问题。很多人发现了这个问题。或许我们没理解对。



[/Quote]我在一个人的博客里看到这句话“InnoDB的可重复读隔离级别和其他数据库的可重复读是有区别的,不会造成幻象读(phantom read),所谓幻象读,

就是同一个事务内,多次select,可以读取到其他session insert并已经commit的数据。”
wh62592855 2009-04-29
  • 打赏
  • 举报
回复
我又做了些试验
发现和表的类型有关系
比如说我把表改为HEAP或者MYISAM时,A事务进行数据修改后即便不COMMIT时B事务就可以读取到数据的变化,而此时我查@@tx_isolation变量发现此时的孤立级别仍然设置的是READ-REPEATABLE

比较奇怪,呵呵
ACMAIN_CHM 2009-04-29
  • 打赏
  • 举报
回复

MySQL的isolate级别一直是个头痛的问题。很多人发现了这个问题。或许我们没理解对。



wh62592855 2009-04-29
  • 打赏
  • 举报
回复
不对啊
幻读的定义大概就是说在你的事务并没有完成的时候可以读到其他事务的插入(修改和删除不行)
wh62592855 2009-04-28
  • 打赏
  • 举报
回复
不是吧。。没人回答 -_-``
wh62592855 2009-04-28
  • 打赏
  • 举报
回复
不是吧。。没人回答 -_-``

56,940

社区成员

发帖
与我相关
我的任务
社区描述
MySQL相关内容讨论专区
社区管理员
  • MySQL
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧