在一个transaction发生的过程中,online redo log首先记录transaction中修改的数据块相关信息,修改的数据块会被缓存在database buffer cache中。由于database buffer cache写满或者checkpoint等等条件触发dbwn进程,会导致这些缓存的数据块写入数据文件,但此时可能该transaction仍然还没有提交。所以在数据文件中,可能会有commited 和 uncommited 的数据块。而原有的数据块镜像会存放在undo segment。IXDBANET社区论坛然而,dbwn写脏数据时不管这个要写的transaction是否提交,也没有必要去管。这样就发生了所谓的已经提交的数据,但是还没有写入数据文件的现象。还有一种情况,数据没有提交,但是已经被写入数据文件,此时发生回退,撤销没有提交的数据。根本原因是commit后写redo buffer和触发lgwr写 redo buffer的区别。事务在执行完毕后,随即会被写入redo buffer和undo中,同时在redo buffer和undo中对该事务都有一个是否提交的标记。两者的默认状态都是active的,即没有提交时刻处于激活状态。commit *** 作执行时刻把此前的所有事务 *** 作全部写入redo log file,commit成功后,redo buffer信息全部写入redo file,同时修改两者中的事务提交标识为inactive,表示此前事务已经递交。oracle的前滚和回退根据就是依据事务是否提交而进行的。在触发lgwr进程后,oracle同样把此前的redo buffer信息写入redo file,但是与commit触发写日志不同的是,redo file本身对lgwr写日志 *** 作不记录任何信息标识,lgwr写到那里就是那里,就算此时掉电也无妨,redo file就记录到掉电时刻的信息。lgwr是一个Oracle后台执行的进程,具体的日志写 *** 作都有oracle去控制,这对于oracle来说是透明的,因此不用在redo file中写入任何标记信息,这也是正常的。于是,Oracle崩溃恢复步骤如下:首先rolling forward 前滚:由于oracle failure,sga中的内存信息丢失了,但是online redo log中还是存储了transaction信息,包括commited or uncommited data。可能这些修改信息并没有被oracle正确的来处理,包含两种情况:已经提交的还没有写入数据文件,或者没有提交的却被写入了数据文件。针对已经提交的还没有写入数据文件就要发生前滚,在前滚过程中,smon会根据online redo log中的记录来完成对datafile的修改。保证已经提交的数据已经写入数据文件。接下来,前滚结束后,数据库正常open,此时用户可以正常连接,可以访问已经recover的commited data,但是对于那些属于unrecoverable transaction的uncommited data,会被oracle 加锁,是不可以访问的。
其实回滚简单理解就是之前 *** 作的反向 *** 作,在addtable1中定义了插入方法,与之相反,回滚的话就是定义一种删除方法,把之前插入的数据删掉就好了。这个你应该可以做到的吧!
还有给你个忠告,以后做数据库 *** 作的时候,最好先备份数据库,这是防止这种情况发生的最简便的方法。
另外,当你要对数据库进行相应的 *** 作的时候,提前分析好回滚 *** 作,特别是逻辑,回滚很容易因为逻辑关系似的数据库面目全非,因为对数据库的 *** 作很多是在 *** 作时候是1-〉2->3->4这样的逻辑,回滚的时候就要进行2->1->4->3这样的逻辑。
如果不行的话再给我留言
以上就是关于Oracle数据库中为什么会产生回滚与前退全部的内容,包括:Oracle数据库中为什么会产生回滚与前退、请问:C# 在做项目中,如何处理 对数据库 *** 作的事务回滚、等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)