11.1.1.2  基于SCN的查询(AS OF SCN)

仍以前文中创建的表为例,既然是基于SCN的查询,我们首先就需要得到SCN,这里我们通过DBMS_FLASHBACK.GET_SYSTEM_CHANGE_NUMBER函数来获取Oracle当前的SCN,之后再执行数据的修改操作

提 示

如何获取Oracle数据库当前的SCN?

获取当前SCN的方式非常多,除了使用DBMS_FLASHBACK.GET_SYSTEM_CHANGE_NUMBER函数外,也可以通过查询V$DATABASE视图中的CURRENT_SCN列获取。不过,不管是通过查询视图,或是通过过程获取,操作的用户都必须拥有要操作对象的访问权限。

例如,授予用户使用DBMS_FLASHBACK包的权限:JSSPRE> CONN/ASSYSDBA

Connected.

JSSPRE>GRANTEXECUTEONDBMS_FLASHBACKTOSCOTT;

Grantsucceeded.

又如,授予用户查询V$DATABASE视图的权限:JSSPRE> CONN/ASSYSDBA

Connected.

JSSPRE>GRANTSELECTONV_$DATABASETOSCOTT;

Grantsucceeded.

使用DBMS_FLASHBACK包获取当前的SCN,然后执行删除操作并提交:JSSPRE>SELECTDBMS_FLASHBACK.GET_SYSTEM_CHANGE_NUMBERFROMDUAL;

GET_SYSTEM_CHANGE_NUMBER

------------------------

1257245

JSSPRE>DELETEFLASH_TBLWHEREID>10;

10rowsdeleted.

JSSPRE>COMMIT;

Commitcomplete.

执行SELECT语句并附加AS OF SCN子句,同时指定删除前的SCN,就可以查询到指定SCN时对象中的记录:JSSPRE>SELECT*FROMFLASH_TBLASOFSCN 1257245;

ID  VL

---------- --

10  K

11  L

12  M

13  N

14  O

15  P

16  Q

17  R

18  S

19  T

20  U

1   A

2   B

3   C

4   D

5   E

6   F

7   G

8   H

9   I

20rowsselected.

执行INSERT,将删除的数据重新恢复回表JSS_TB1:JSSPRE>INSERTINTOFLASH_TBLSELECT*FROMFLASH_TBL

ASOFSCN 1257245WHEREID>10;

10rowscreated.

JSSPRE>commit;

Commitcomplete.

使用SCN查询会比TIMESTAMP更加精确,事实上,即使执行Flashback Query时指定的是AS OF TIMESTAMP,Oracle也会将其转换成SCN,这是由于Oracle内部都是通过SCN来标记操作而不是时间。

不过在实际执行Flashback Query时,时间转换后具体对应哪个SCN,是通过SYS用户下的一个数据字典实现的,即SMON_SCN_TIME(时间与SCN的映射关系表):JSSPRE>DESCSYS.SMON_SCN_TIME;

NameNull?       Type

------------------     --------    ---------------

THREAD                         NUMBER

TIME_MP                        NUMBER

TIME_DPDATE

SCN_WRP                        NUMBER

SCN_BAS                        NUMBER

NUM_MAPPINGS               NUMBER

TIM_SCN_MAP                    RAW(1200)

SCN                            NUMBER

ORIG_THREAD                    NUMBER

在10g中,系统平均每3秒产生一次系统时间与SCN的匹配并存入SYS.SMON_SCN_ TIME表,因此10g版本如果使用AS OF TIMESTAMP查询UNDO中的数据,实际获取的数据是以指定的时间对应的SCN时的数据为基准。

举个例子,如SCN:339988,339989分别匹配2009-05-30 13:52:00和2009-05-30 13:57:00,则当你通过AS OF TIMESTAMP查询2009-05-30 13:52:00或2009-05-30 13:56:59这段时间点内的任何时间,oracle都会将其匹配为SCN:339988到UNDO表空间中查找,也就说在这个时间内,不管你指定的时间点是什么,查询返回的都将是2009-05-30 13:52:00这个时刻对应的SCN的数据。如果通过上述文字的描述仍觉得不够形象,我想你亲自执行一下SELECT SCN,TO_CHAR(TIME_DP,'YYYY-MM-DD HH24:MI:SS')FROM SYS.SMON_ SCN_TIME,会理解得更深刻一些。

在Oracle数据库中也可以手动进行时间和SCN的相互转换,Oracle提供了两个函数SCN_TO_TIMESTAMP和TIMESTAMP_TO_SCN专门干这个,例如:JSSPRE>SELECTTIMESTAMP_TO_SCN(SYSDATE)FROMDUAL;

TIMESTAMP_TO_SCN(SYSDATE)

-------------------------

1263291

JSSPRE>SELECTTO_CHAR(SCN_TO_TIMESTAMP(1263291),

'YYYY-MM-DD')FROMDUAL;

TO_CHAR(SC

----------

2009-06-02

提 示

上面的示例中TIMESTAMP类型经过TO_CHAR格式化,只显示了日期,千万别以为只能精确到日期哟。Oracle中的TIMESTAMP日期类型***能够精确到纳秒(不过一般操作系统返回的精度只到毫秒,因此即使格式化显示出纳秒的精度也没意义,毫秒后就全是零了)。

看起来很强大吧?其实这两个函数的转换依赖于SYS.SMON_SCN_TIME表,能够转换到的最小SCN,也正是这个表中的最小记录,例如:JSSPRE>SELECTSCN_WRP*4294967296+SCN_BASFROMSYS.SMON_SCN_TIME

2WHERETIME_MP=(SELECTMIN(TIME_MP)FROMSYS.SMON_SCN_TIME);

SCN_WRP*4294967296+SCN_BAS

--------------------------

554140

能够转换到的最小SCN值是554140,使用SCN_TO_TIMESTAMP查询该SCN对应的时间:JSSPRE>SELECTSCN_TO_TIMESTAMP(554140)FROMDUAL;

SCN_TO_TIMESTAMP(554140)

---------------------------------------------------------------------------

21-MAR-09 11.51.30.000000000 PM

比该SCN哪怕只再小1的值也无法转换了,因为SYS.SMON_SCN_TIME表中没有对应的映射关系:JSSPRE>SELECTSCN_TO_TIMESTAMP(554139)FROMDUAL;

selectscn_to_timestamp(554139)fromdual

*

ERRORatline 1:

ORA-08181: specified numberisnota valid system change number

ORA-06512:at"SYS.SCN_TO_TIMESTAMP", line 1

时间的转换也是同理,所以你看,如果SYS.SMON_SCN_TIME表中不存在时间和SCN的映射关系,则执行函数转换时就会报错,也就是说时间和SCN之间并不存在绝对的对应关系。一切都是Oracle提供给你的,只有当它愿意让你看,你才能够看到。

【责任编辑:董书 TEL:(010)68476606】

点赞 0

获取当前scn号scn1_11.1.1.2 基于SCN的查询(AS OF SCN)相关推荐

  1. 获取当前scn号scn1_Checkpoint和SCN的解析

    Checkpoint 很多人都把checkpoint的概念给复杂化了,其实checkpoint这个数据库概念引入的真正意义就是用来减少在数据库恢复过程中所花的时间(instance recovery) ...

  2. 获取当前scn号scn1_Oracle 系统改变号SCN详解

    Scn : scn的英文全称就是 system change number, 中文直译过来就是系统改变号了. 1.SCN的定义 scn的英文全称就是 system change number, 中文直 ...

  3. 获取当前scn号scn1_深入理解SCN号

    在oracle中存在很多种scn,但是,只有如下几种是我们比较关注的. commit scn/cleanout scn database scn/on disk scn/thread scn/data ...

  4. 手动修改oracle scn号,SCN(系统改变号)

    1. scn: system change number 用以标识数据库在某个确切时刻提交的版本. 数据库的内部逻辑时钟. 每个数据库都有一个全局的SCN生成器. 它会随着外部变化的加快而加快变化,在 ...

  5. oracle技术之检查点及SCN号(一)

    一.CHECKPIONT分为三类: 1)局部CHECKPIONT: 单个实例执行数据库所有数据文件的一个CHECKPIONT操作,属于此实例的全部脏缓存区写入数据文件. 触发命令:SQL>alt ...

  6. [分享]C# 获取Outlook帐号和密码

    [分享]C# 获取Outlook帐号和密码 http://www.vjsdn.com/bbs/bbsTopicDetails.aspx?pid=108281214 转载于:https://www.cn ...

  7. 用公众号获取 任意公众号文章列表 软件还是免费

    用公众号获取 任意公众号文章列表 软件还是免费还不快点下载 下载 地址  https://pan.baidu.com/s/1jI44Wjs 转载于:https://www.cnblogs.com/wx ...

  8. Python通过snmp获取交换机VLAN号、VLAN默认网关、VLAN子网掩码和ARP表中的IP地址与MAC对应记录数据

    自己做项目时,自己封装的Python通过snmp获取交换机VLAN号.VLAN默认网关.VLAN子网掩码和ARP表中的IP地址与MAC对应记录数据. myPySnmp.py源代码 "&quo ...

  9. 获取登录域帐号信息方式之 —-IIS(VB)

    前言 java web 项目如何获取客户端登录帐号信息(用于SSO或其他) 之前总结过一篇在Java 的Web 项目中获取客户端帐号信息的文章.参见以上链接的内容. 除了那些方式之外, 还可以使用II ...

最新文章

  1. 对比:Linux和Windows系统线程间的区别
  2. AndoridSQLite数据库开发基础教程(6)
  3. android lint 空指针,HardwareRenderer中的NullPointerException
  4. owls-uddi-matchmaker安装
  5. Spring Boot通过配置文件区分测试和生产环境
  6. 绝命毒师口语精析(3)
  7. OpenCV入门: Mat数据类型及其转换,访问
  8. python—scipy.stats.multivariate_normal
  9. PE启动盘制作,电脑PE工具制作教程(可能是最详细的制作方法)小白推荐
  10. 手机邮箱如何申请注册?163邮箱申请哪个好?
  11. 嵌入式课程设计第一篇之OLED与温湿度模块
  12. Ubuntu中解压缩命令
  13. 2009年最值得注意炒作题材
  14. MySQL入门系列:查询简介(二) 过滤数据
  15. python 打开excel并在屏幕上呈现_如何用Python打开Excel文件显示其内容?
  16. 任何经历,都是一种积累
  17. 扫地机器人的技术升级之路 自主规划清扫成主流
  18. 微信扫码登录自定义二维码样式
  19. 启动数据库MySQL
  20. 关于特征值特征向量和矩阵分解的理解总结

热门文章

  1. 拆解任務與目標、按時完成,不再被deadline追著跑
  2. django中的querydict对象_Django之MTV实战(2)
  3. java注释越多_java 注释+常便量
  4. 还原oracle控制文件位置,oracle 11.2 控制文件还原
  5. Mysql多表关联查询
  6. HTTPRunner学习笔记
  7. 资深面试官解答:大厂月薪过20K的测试工程师,都需要满足哪些要求?
  8. 如何学好Python自动化,每个进阶的测试人都应该看看
  9. 六年级下册百分数计算题_六年级数学上册期末试卷(附答案)
  10. win10下装win7双系统_电脑安装双系统win7+win10,安装顺序不同,使用会有什么不同?...