使用rowid和rownum获取记录时要注意的问题

SQL> select rowid,rownum,object_id,object_name from test1;

 

ROWID                  ROWNUM  OBJECT_ID OBJECT_NAME

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

AAAM+rAAGAAAACUAAA          1         20 ICOL$

AAAM+rAAGAAAACUAAB          2         44 I_USER1

AAAM+rAAGAAAACUAAC          3         28 CON$

AAAM+rAAGAAAACUAAD          4         15 UNDO$

AAAM+rAAGAAAACUAAE          5         29 C_COBJ#

AAAM+rAAGAAAACUAAF          6          3 I_OBJ#

AAAM+rAAGAAAACUAAG          7         25 PROXY_ROLE_DATA$

AAAM+rAAGAAAACUAAH          8         39 I_IND1

AAAM+rAAGAAAACUAAI          9         51 I_CDEF2

AAAM+rAAGAAAACUAAJ        10         26 I_PROXY_ROLE_DATA$_1

 

10 rows selected.

 

把列名全部显示指定,可以看到,rowid和rownum这两列的内容也都显示了。那我们能不能用rowid列来作为查找条件呢?当然是可以的,但前提是你要知道rowid值是怎么分布的

 

SQL> select rowid,object_id,object_name from test1 where rowid<to_char('AAAM+rAAGAAAACUAAK');

 

ROWID               OBJECT_ID OBJECT_NAME

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

AAAM+rAAGAAAACUAAA         20 ICOL$

AAAM+rAAGAAAACUAAB         44 I_USER1

AAAM+rAAGAAAACUAAC         28 CON$

AAAM+rAAGAAAACUAAD         15 UNDO$

AAAM+rAAGAAAACUAAE         29 C_COBJ#

AAAM+rAAGAAAACUAAF          3 I_OBJ#

AAAM+rAAGAAAACUAAG         25 PROXY_ROLE_DATA$

AAAM+rAAGAAAACUAAH         39 I_IND1

AAAM+rAAGAAAACUAAI         51 I_CDEF2

AAAM+rAAGAAAACUAAJ         26 I_PROXY_ROLE_DATA$_1

 

10 rows selected.

 

为什么条件是<to_char('AAAM+rAAGAAAACUAAK')?因为通过刚才的观察,我们知道test1表中的第10条记录是到J,那么要获取这10条记录,就是比AAK小的这些记录

 

这里来说明一下rowid中这些字母表示的含义:

 

在Oracle 8以下,rowid(也叫受限rowid)为:FFFF.BBBBBBBB.RRRR,占用6个字节(10bit file#+22bit+16bit),但是,为了扩充的需要,如数据文件的扩充,现在的rowid改为:OOOOOOFFFBBBBBBRRR,占用10个字节(32bit+10bit rfile#+22bit+16bit)。其中,O是Object号,F是File号,B是Block号,R是Row号。由于rowid的组成从file#变成了rfile#,所以数据文件数的限制也从整个库不能超过1023个变成了每个表空间不能超过1023个数据文件这里的object_id,是与段物理存储位置相关的一个信息,因为一个段对象只可能在一个表空间上,object_id能唯一确认ts#,而object_id + rfile#就能最终定位到该rowid在哪个确定的物理数据文件上

 

因此,这里的AAG就表示这是第6个数据文件,要注意的是,AAA从0开始计数,行号也是如此。因此,AAA-AAJ就表示是test1表中的1-10行记录(0->9)

 

SQL> col name for a45

SQL> select file#,name from v$datafile;

 

     FILE# NAME

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

         1 /u01/app/oracle/oradata/ora10g/system01.dbf

         2 /u01/app/oracle/oradata/ora10g/undotbs01.dbf

         3 /u01/app/oracle/oradata/ora10g/sysaux01.dbf

         4 /u01/app/oracle/oradata/ora10g/users01.dbf

         5 /u01/app/oracle/oradata/ora10g/example01.dbf

         6 /u01/app/oracle/oradata/ora10g/zlm01.dbf

 

zlm用户默认的表空间就是zlm,其对应的数据文件就是zlm01.dbf,可以看到,file#为6而并不是7

 

我们还可以用Oracle提供的dbms.rowid包来根据rowid的值来获取object_id#,rfile#,block#,row#这些具体的值:

 

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/fb114b4e2126a9987bbbb6af660ba61c.html