Flashback Query!

首先创建一个测试表

SQL> conn /as sysdba
已连接。
SQL> select file_name from dba_data_files;

FILE_NAME
--------------------------------------------------------------------------------
/u01/app/oracle/oradata/orcl/users01.dbf
/u01/app/oracle/oradata/orcl/sysaux01.dbf
/u01/app/oracle/oradata/orcl/undotbs01.dbf
/u01/app/oracle/oradata/orcl/system01.dbf

SQL> create tablespace tb1 datafile '/u01/app/oracle/oradata/orcl/tb1.dbf' size 10m;

表空间已创建。

SQL> create user u1 identified by u1 default tablespace tb1;

用户已创建。

SQL> grant connect,resource to u1;

授权成功。

SQL> conn u1/u1
已连接。

SQL> create table t(id int,value varchar2(10));

表已创建。

SQL> insert into t values(1,'a');

已创建 1 行。

SQL> commit;

提交完成。

SQL> select * from t;

        ID VALUE
---------- ----------
         1 a

1  基于时间的查询(AS OF TIMESTAMP)

SQL> select sysdate from dual;

SYSDATE
-------------------
2011-10-18 06:14:06

SQL> insert into t values(2,'b');

已创建 1 行。

SQL> commit;

提交完成。

SQL> select * from t;

        ID VALUE
---------- ----------
         1 a
         2 b

SQL> select * from t as of timestamp to_date('2011-10-18 06:14:06','yyyy-mm-dd hh24:mi:ss');

        ID VALUE
---------- ----------
         1 a

SQL> select * from t as of timestamp sysdate-5/1440;         --查询5分钟以前的数据

        ID VALUE
---------- ----------
         1 a
说明:60(分)×24=1440,这样就计算出一天拥有多少分钟。SYSDATE-5/1440,得出的就是距当前时间5分钟前的记录了。

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

SQL> conn /as sysdba
已连接。
SQL> select current_scn from v$database;

CURRENT_SCN
-----------
     474847

SQL> conn u1/u1
已连接。
SQL> insert into t values(3,'c');

已创建 1 行。

SQL> commit;

提交完成。

SQL> select * from t;

        ID VALUE
---------- ----------
         1 a
         2 b
         3 c

SQL> select * from t as of scn 474847;

        ID VALUE
---------- ----------
         1 a
         2 b

3 SCN和时间的对应关系

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

查询scn和时间的对应关系

SQL> conn /as sysdba
已连接。
SQL> select scn,to_char(time_dp,'yyyy-mm-dd hh24:mi:ss') from smon_scn_time;

       SCN TO_CHAR(TIME_DP,'YY
---------- -------------------
         4 2008-02-17 01:50:43
     10725 2008-02-17 01:51:16
    114369 2008-02-17 01:56:49
    160566 2008-02-17 02:01:21
    238143 2008-02-17 02:06:31
    296479 2008-02-17 02:11:17
    340068 2008-02-17 02:17:22
    380836 2008-02-17 02:21:18
    428625 2008-02-17 02:26:36
    438655 2008-02-17 02:28:33
    438698 2008-02-17 02:28:34

       SCN TO_CHAR(TIME_DP,'YY
---------- -------------------
    461085 2008-02-17 02:29:13
    461400 2008-02-17 02:29:36
    463047 2008-02-17 02:29:50
    464634 2011-10-18 05:53:12
    473110 2011-10-18 05:54:17
    473423 2011-10-18 05:54:40
    473499 2011-10-18 05:54:43
    474181 2011-10-18 05:59:47
    474185 2011-10-18 05:59:57
    474286 2011-10-18 06:04:57
    474635 2011-10-18 06:10:12

       SCN TO_CHAR(TIME_DP,'YY
---------- -------------------
    474735 2011-10-18 06:14:57

已选择23行。

把时间转换为scn

SQL> select timestamp_to_scn(sysdate) from dual;

TIMESTAMP_TO_SCN(SYSDATE)
-------------------------
                   474991

把scn转换为时间

SQL> select to_char(scn_to_timestamp(474991),'yyyy-mm-dd hh24:mi:ss') from dual;

TO_CHAR(SCN_TO_TIME
-------------------
2011-10-18 06:25:22

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

你可能感兴趣的:(oracle,sql,Date,table,query,insert)