SQL> col object_name FOR a40
SQL>SETLINES120
SQL> l
1*SELECT owner,object_name,object_type FROM dba_objects WHERE object_name=UPPER('flashback_transaction_query')
SQL>/
OWNER OBJECT_NAME OBJECT_TYPE
---------- ------------------------------ -------------------
SYS FLASHBACK_TRANSACTION_QUERY VIEW
PUBLIC FLASHBACK_TRANSACTION_QUERY SYNONYM
SQL>SELECT dbms_metadata.get_ddl('VIEW','FLASHBACK_TRANSACTION_QUERY')FROM dual;
DBMS_METADATA.GET_DDL('VIEW','FLASHBACK_TRANSACTION_QUERY')--------------------------------------------------------------------------------CREATEORREPLACE FORCE VIEW"SYS"."FLASHBACK_TRANSACTION_QUERY"("XID","STAR
T_SCN","START_TIMESTAMP","COMMIT_SCN","COMMIT_TIMESTAMP","LOGON_USER","UNDO
_CHANGE#","OPERATION","TABLE_NAME","TABLE_OWNER","ROW_ID","UNDO_SQL")ASSELECT xid, start_scn, start_timestamp,
decode(commit_scn,0, commit_scn,281474976710655,NULL, commit_scn)
commit_scn, commit_timestamp,
logon_user, undo_change#, operation,TABLE_NAME, table_owner,
row_id, undo_sql
FROM sys.x$ktuqqry
SQL>
SQL>SELECTCOUNT(1)FROM FLASHBACK_TRANSACTION_QUERY;
COUNT(1)----------45018
SQL>SELECTCOUNT(1)FROM sys.x$ktuqqry
2 ;
COUNT(1)----------45018
SQL>
该x$表的表结构如下:
SQL> desc x$ktuqqry
Name Null? Type
--------------------- -------- -----------------------
ADDR RAW(4)
INDX NUMBER
INST_ID NUMBER
XID RAW(8)
START_SCN NUMBER
START_TIMESTAMP DATE
COMMIT_SCN NUMBER
COMMIT_TIMESTAMP DATE
LOGON_USER VARCHAR2(30)
UNDO_CHANGE# NUMBER
OPERATION VARCHAR2(32)
TABLE_OWNER VARCHAR2(32)
TABLE_NAME VARCHAR2(256)
ROW_ID VARCHAR2(19)
UNDO_SQL VARCHAR2(4000)
既然是关于闪回方面的技术,那么显然也就是跟undo有关系了,我们来检查下undo信息:
SQL>SHOW parameter undo
NAME TYPEVALUE------------------------------------ ----------- -------------------
_gc_undo_affinity BOOLEANFALSE
undo_management string AUTO
undo_retention INTEGER900
undo_tablespace string UNDOTBS1
SQL>SELECT owner,segment_name,SEGMENT_ID,FILE_ID,BLOCK_ID,INITIAL_EXTENT,NEXT_EXTENT,MAX_EXTENTS,STATUSFROM dba_rollback_segs;
OWNER SEGMENT_NAME SEGMENT_ID FILE_ID BLOCK_ID INITIAL_EXTENT NEXT_EXTENT MAX_EXTENTS STATUS------ -------------- ---------- ---------- ---------- -------------- ----------- ----------- ----------------
SYS SYSTEM 0191146885734432765 ONLINE
PUBLIC _SYSSMU1$ 1291310726553632765 ONLINE
PUBLIC _SYSSMU2$ 22251310726553632765 ONLINE
PUBLIC _SYSSMU3$ 32411310726553632765 ONLINE
PUBLIC _SYSSMU4$ 42571310726553632765 ONLINE
PUBLIC _SYSSMU5$ 52731310726553632765 ONLINE
PUBLIC _SYSSMU6$ 62891310726553632765 ONLINE
PUBLIC _SYSSMU7$ 721051310726553632765 ONLINE
PUBLIC _SYSSMU8$ 821211310726553632765 ONLINE
PUBLIC _SYSSMU9$ 921371310726553632765 ONLINE
PUBLIC _SYSSMU10$ 1021531310726553632765 ONLINE
PUBLIC RBS_001 11213211310726553632765 OFFLINE
12ROWS selected.
SQL> oradebug setmypid
Statement processed.
SQL>ALTER system dump undo header 'SYSTEM';
System altered.
SQL>ALTER system dump undo header '_SYSSMU1$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU2$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU3$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU4$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU5$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU6$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU7$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU8$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU9$';
System altered.
SQL>ALTER system dump undo header '_SYSSMU10$';
System altered.
SQL>ALTER system dump undo header 'RBS_001';
System altered.
SQL> oradebug tracefile_name
/home/ora10g/admin/roger/udump/roger_ora_15306.trc
SQL>-------trace[ora10g@killdb udump]$ cat /home/ora10g/admin/roger/udump/roger_ora_15306.trc| grep TRN
TRN CTL:: seq: 0x0059 chd: 0x001a ctl: 0x000c inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x041a chd: 0x0025 ctl: 0x000d inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x079e chd: 0x0005 ctl: 0x0018 inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x0324 chd: 0x0015 ctl: 0x0022 inc: 0x00000000 nfb: 0x0002
TRN TBL::
TRN CTL:: seq: 0x04e0 chd: 0x001c ctl: 0x000d inc: 0x00000000 nfb: 0x0003
TRN TBL::
TRN CTL:: seq: 0x03d0 chd: 0x0028 ctl: 0x002e inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x063f chd: 0x001d ctl: 0x0009 inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x06c0 chd: 0x0026 ctl: 0x0008 inc: 0x00000000 nfb: 0x0002
TRN TBL::
TRN CTL:: seq: 0x0472 chd: 0x000e ctl: 0x0011 inc: 0x00000000 nfb: 0x0003
TRN TBL::
TRN CTL:: seq: 0x04f3 chd: 0x002f ctl: 0x0001 inc: 0x00000000 nfb: 0x0002
TRN TBL::
TRN CTL:: seq: 0x040e chd: 0x0024 ctl: 0x0025 inc: 0x00000000 nfb: 0x0001
TRN TBL::
TRN CTL:: seq: 0x0001 chd: 0x0001 ctl: 0x0000 inc: 0x00000000 nfb: 0x0001
TRN TBL::
SQL>SELECT89+1050+1950+804+1248+976+1599+1728+1138+1267+1038+1FROM dual;
89+1050+1950+804+1248+976+1599+1728+1138+1267+1038+1----------------------------------------------------12888
我们可以看到,我们使用闪回查询常用的几个字段的选择性可以说都很低,这或许就是为什么oracle不给相应的字段添加index的原因之一。 另外一种原因我猜测可能是:通常来讲,一个事务可能涉及到很多记录数,这样就比如导致xid的选择性很低,那么再去创建index 意义 也就不大了。其实我在想,如果有index的话,或许会走index fast full scan,起码也要比全表扫描要快的多。
那么是不是就没有办法了呢? 突然我想到可以利用物化视图俩满足该网友的需求,如下:
SQL>SET timing ON
SQL>ALTER system FLUSH BUFFER_CACHE;
System altered.
Elapsed: 00:00:00.02
SQL>ALTER system FLUSH SHARED_POOL;
System altered.
Elapsed: 00:00:00.01
SQL>SET autot traceonly
SQL>SELECT*FROM FLASHBACK_TRANSACTION_QUERY WHERE xid='1400210042060000';
no ROWS selected
Elapsed: 00:00:04.66
Execution Plan
----------------------------------------------------------
Plan hash VALUE: 1115820779------------------------------------------------------------------------------| Id | Operation | Name |ROWS| Bytes | Cost (%CPU)|TIME|------------------------------------------------------------------------------|0|SELECT STATEMENT ||28|2464|7(100)| 00:00:01 ||*1| FIXED TABLEFULL| X$KTUQQRY |28|2464|7(100)| 00:00:01 |------------------------------------------------------------------------------
Predicate Information (IDENTIFIEDBY operation id):
---------------------------------------------------1-FILTER(RAWTOHEX("XID")='1400210042060000')
Statistics
----------------------------------------------------------7458 recursive calls
20 db block gets
82646 consistent gets
1885 physical reads
0 redo SIZE993 bytes sent via SQL*Net TO client
408 bytes received via SQL*Net FROM client
1SQL*Net roundtrips TO/FROM client
338 sorts (memory)0 sorts (disk)0ROWS processed
SQL>CREATE materialized VIEW flash_query_test ASSELECT*FROM FLASHBACK_TRANSACTION_QUERY;
Materialized VIEW created.
Elapsed: 00:00:02.33
SQL>CREATEINDEX xid_idx ON flash_query_test(xid);
INDEX created.
Elapsed: 00:00:00.37
SQL> analyze INDEX xid_idx compute statistics;
INDEX analyzed.
Elapsed: 00:00:00.42
SQL>SET autot traceonly
SQL>SELECT*FROM flash_query_test WHERE xid='1400210042060000';
no ROWS selected
Elapsed: 00:00:00.23
Execution Plan
----------------------------------------------------------
Plan hash VALUE: 962280044-----------------------------------------------------------------------------------------| Id | Operation | Name |ROWS| Bytes | Cost (%CPU)|TIME|-----------------------------------------------------------------------------------------|0|SELECT STATEMENT ||4|9036|99(2)| 00:00:01 ||*1| MAT_VIEW ACCESS FULL| FLASH_QUERY_TEST |4|9036|99(2)| 00:00:01 |-----------------------------------------------------------------------------------------
Predicate Information (IDENTIFIEDBY operation id):
---------------------------------------------------1-FILTER(RAWTOHEX("XID")='1400210042060000')
Note
------ dynamic sampling used FOR this statement (level=2)
Statistics
----------------------------------------------------------9 recursive calls
0 db block gets
428 consistent gets
357 physical reads
0 redo SIZE993 bytes sent via SQL*Net TO client
408 bytes received via SQL*Net FROM client
1SQL*Net roundtrips TO/FROM client
0 sorts (memory)0 sorts (disk)0ROWS processed