一. 数据字典表SYS.COL$ 说明
Oracle 的数据字典分两类,一个数据字典表,另一个是数据字典视图。
数据字典表里的数据是Oracle系统存放的系统数据,而普通表存放的是用户的数据。为了方便的区别这些表,这些表的名字都是用"$"结尾,这些表属于SYS用户。
数据字典表由$ORACLE_HOME/rdbms/admin/sql.bsq 脚本创建。
这些数据字典表名称不好记,所以Oracle 又根据这些表创建了一些视图。 即方便使用,又影藏了那些数据字典表。
关于数据字典的更多内容,参考我的Blog:
Oracle 数据字典 说明
http://blog.csdn.net/tianlesoftware/archive/2010/09/04/5862508.aspx
这里讲的SYS.COL$表保存的就是表列的定义信息,但是我们查询表列的信息时,却不是直接查询SYS.COL$,而是查询USER_TAB_COLUMNS 视图。
SQL> select owner,object_name,object_type from all_objects where object_name='COL$';
OWNER OBJECT_NAME OBJECT_TYPE
----------------- ------------------------------ ------------------
SYS COL$ TABLE
SQL> set long 9999
SQL> select text from dba_views where view_name ='USER_TAB_COLUMNS';
TEXT
--------------------------------------------------------------------------------
select TABLE_NAME, COLUMN_NAME, DATA_TYPE, DATA_TYPE_MOD, DATA_TYPE_OWNER,
DATA_LENGTH, DATA_PRECISION, DATA_SCALE, NULLABLE, COLUMN_ID,
DEFAULT_LENGTH, DATA_DEFAULT, NUM_DISTINCT, LOW_VALUE, HIGH_VALUE,
DENSITY, NUM_NULLS, NUM_BUCKETS, LAST_ANALYZED, SAMPLE_SIZE,
CHARACTER_SET_NAME, CHAR_COL_DECL_LENGTH,
GLOBAL_STATS, USER_STATS, AVG_COL_LEN, CHAR_LENGTH, CHAR_USED,
V80_FMT_IMAGE, DATA_UPGRADED, HISTOGRAM
from USER_TAB_COLS
where HIDDEN_COLUMN = 'NO'
这里查看的是USER_TAB_COLS视图,我们在挖一层:
SQL>select * from dba_views where view_name ='USER_TAB_COLS'
select o.name,
c.name,
decode(c.type#, 1, decode(c.charsetform, 2, 'NVARCHAR2', 'VARCHAR2'),
2, decode(c.scale, null,
decode(c.precision#, null, 'NUMBER', 'FLOAT'),
'NUMBER'),
8, 'LONG',
9, decode(c.charsetform, 2, 'NCHAR VARYING', 'VARCHAR'),
12, 'DATE',
23, 'RAW', 24, 'LONG RAW',
58, nvl2(ac.synobj#, (select o.name from obj$ o
where o.obj#=ac.synobj#), ot.name),
69, 'ROWID',
96, decode(c.charsetform, 2, 'NCHAR', 'CHAR'),
100, 'BINARY_FLOAT',
101, 'BINARY_DOUBLE',
105, 'MLSLABEL',
106, 'MLSLABEL',
111, nvl2(ac.synobj#, (select o.name from obj$ o
where o.obj#=ac.synobj#), ot.name),
112, decode(c.charsetform, 2, 'NCLOB', 'CLOB'),
113, 'BLOB', 114, 'BFILE', 115, 'CFILE',
121, nvl2(ac.synobj#, (select o.name from obj$ o
where o.obj#=ac.synobj#), ot.name),
122, nvl2(ac.synobj#, (select o.name from obj$ o
where o.obj#=ac.synobj#), ot.name),
123, nvl2(ac.synobj#, (select o.name from obj$ o
where o.obj#=ac.synobj#), ot.name),
178, 'TIME(' ||c.scale|| ')',
179, 'TIME(' ||c.scale|| ')' || ' WITH TIME ZONE',
180, 'TIMESTAMP(' ||c.scale|| ')',
181, 'TIMESTAMP(' ||c.scale|| ')' || ' WITH TIME ZONE',
231, 'TIMESTAMP(' ||c.scale|| ')' || ' WITH LOCAL TIME ZONE',
182, 'INTERVAL YEAR(' ||c.precision#||') TO MONTH',
183, 'INTERVAL DAY(' ||c.precision#||') TO SECOND(' ||
c.scale || ')',
208, 'UROWID',
'UNDEFINED'),
decode(c.type#, 111, 'REF'),
nvl2(ac.synobj#, (select u.name from "_BASE_USER" u, obj$ o
where o.owner#=u.user# and o.obj#=ac.synobj#),
ut.name),
c.length, c.precision#, c.scale,
decode(sign(c.null$),-1,'D', 0, 'Y', 'N'),
decode(c.col#, 0, to_number(null), c.col#), c.deflength,
c.default$, h.distcnt, h.lowval, h.hival, h.density, h.null_cnt,
case when nvl(h.distcnt,0) = 0 then h.distcnt
when h.row_cnt = 0 then 1
when (h.bucket_cnt > 255
or
(h.bucket_cnt > h.distcnt
and h.row_cnt = h.distcnt
and h.density*h.bucket_cnt < 1))
then h.row_cnt
else h.bucket_cnt
end,
h.timestamp#, h.sample_size,
decode(c.charsetform, 1, 'CHAR_CS',
2, 'NCHAR_CS',
3, NLS_CHARSET_NAME(c.charsetid),
4, 'ARG:'||c.charsetid),
decode(c.charsetid, 0, to_number(NULL),
nls_charset_decl_len(c.length, c.charsetid)),
decode(bitand(h.spare2, 2), 2, 'YES', 'NO'),
decode(bitand(h.spare2, 1), 1, 'YES', 'NO'),
h.avgcln,
c.spare3,
decode(c.type#, 1, decode(bitand(c.property, 8388608), 0, 'B', 'C'),
96, decode(bitand(c.property, 8388608), 0, 'B', 'C'),
null),
decode(bitand(ac.flags, 128), 128, 'YES', 'NO'),
decode(o.status, 1, decode(bitand(ac.flags, 256), 256, 'NO', 'YES'),
decode(bitand(ac.flags, 2), 2, 'NO',
decode(bitand(ac.flags, 4), 4, 'NO',
decode(bitand(ac.flags, 8), 8, 'NO',
'N/A')))),
decode(c.property, 0, 'NO', decode(bitand(c.property, 32), 32, 'YES',
'NO')),
decode(c.property, 0, 'NO', decode(bitand(c.property, 8), 8, 'YES',
'NO')),
decode(c.segcol#, 0, to_number(null), c.segcol#), c.intcol#,
case when nvl(h.row_cnt,0) = 0 then 'NONE'
when (h.bucket_cnt > 255
or
(h.bucket_cnt > h.distcnt and h.row_cnt = h.distcnt
and h.density*h.bucket_cnt < 1))
then 'FREQUENCY'
else 'HEIGHT BALANCED'
end,
decode(bitand(c.property, 1024), 1024,
(select decode(bitand(cl.property, 1), 1, rc.name, cl.name)
from sys.col$ cl, attrcol$ rc where cl.intcol# = c.intcol#-1
and cl.obj# = c.obj# and c.obj# = rc.obj#(+) and
cl.intcol# = rc.intcol#(+)),
decode(bitand(c.property, 1), 0, c.name,
(select tc.name from sys.attrcol$ tc
where c.obj# = tc.obj# and c.intcol# = tc.intcol#)))
from sys.col$ c, sys."_CURRENT_EDITION_OBJ" o, sys.hist_head$ h,
sys.coltype$ ac, sys.obj$ ot, sys."_BASE_USER" ut
where o.obj# = c.obj#
and bitand(o.flags, 128) = 0
and o.owner# = userenv('SCHEMAID')
and c.obj# = h.obj#(+) and c.intcol# = h.intcol#(+)
and c.obj# = ac.obj#(+) and c.intcol# = ac.intcol#(+)
and ac.toid = ot.oid$(+)
and ot.type#(+) = 13
and ot.owner# = ut.user#(+)
and (o.type# in (3, 4) /* cluster, view */
or
(o.type# = 2 /* tables, excluding iot - overflow and nested tables */
and
not exists (select null
from sys.tab$ t
where t.obj# = o.obj#
and (bitand(t.property, 512) = 512 or
bitand(t.property, 8192) = 8192))))
在这里,我们看到了本质:sys.col$ 。
Oracle数据库没有提供直接修改表中列名称的功能,但在实际使用时常需要修改表的列名和列顺序。
我们可以通过间接的方法来实现,就是重新创建一个新的具有正确列名和顺序的数据库表,再将旧表的数据转储进来,最后删除旧表并将新表重命名为旧表的方法来完成此功能。
这种方法的最大问题是要求有双倍的存储空间、较大的回滚段和较长的时间,如果表中数据量较大,这项工作开销会很大。
而SYS.COL$保存的就是表列的信息,所以我们可以直接修改这个表列的信息,从而改变表中列的顺序。 当然Oracle 是不建议这么操作的。 这里也只做个知识点了解一下。
二. SYS.COL$ 示例
2.1 创建测试表
SQL> conn dave/dave;
已连接。
SQL> create table myuser as select username,user_id from all_users;
表已创建。
SQL> select * from myuser where rownum=1;
USERNAME USER_ID
------------------------------ ----------
DAVE 90
下面的操作就是将2个列换一下顺序,并将列名改为ID 和 NAME.
2. 2 从ALL_OBJECTS中查找对象DAVE.MYUSER表的ID
在第一节里我们将了,对象的表列信息是存放在SYS.COL$表里的,要修改对象的列,就需要知道对象的ID.
SQL> SELECT OBJECT_NAME,OBJECT_ID FROM ALL_OBJECTS WHERE OWNER ='DAVE' AND OBJECT_NAME='MYUSER';
OBJECT_NAME OBJECT_ID
------------------------------ ----------
MYUSER 74344
2.3根据MYUSER的ID,从SYS.COL$检索出表中列的定义信息
SQL> conn / as sysdba;
已连接。
SQL> SELECT OBJ#,COL#,NAME FROM SYS.COL$ WHERE OBJ# =74344;
OBJ# COL# NAME
---------- ---------- ------------------------------
74344 1 USERNAME
74344 2 USER_ID
注意:SYS.COL$ 只能sys 用户才有权限查询。
2.4 使用Update语句来进行修改
SQL> UPDATE SYS.COL$ SET COL# = 1,NAME='ID' WHERE OBJ# = 74344 AND NAME='USER_ID';
已更新 1 行。
SQL> UPDATE SYS.COL$ SET COL# = 2,NAME='NAME' WHERE OBJ# = 74344 AND NAME ='USERNAME';
已更新 1 行。
SQL> COMMIT;
提交完成。
2.5 重启数据库服务
由于数据字典是在数据库启动时加载到SQL中的,所以修改了它之后,还需要重启数据库服务。
SQL> shutdown immediate;
数据库已经关闭。
已经卸载数据库。
ORACLE 例程已经关闭。
SQL> startup
ORACLE 例程已经启动。
Total System Global Area 1071333376 bytes
Fixed Size 1375792 bytes
Variable Size 436208080 bytes
Database Buffers 629145600 bytes
Redo Buffers 4603904 bytes
数据库装载完毕。
数据库已经打开。
SQL>
2.6 再查看
SQL> conn dave/dave;
已连接。
SQL> select * from myuser where rownum=1;
ID NAME
---------- ------------------------------
90 DAVE
修改已经成功。
直接修改数据字典表是个危险的操作。 所以以上测试仅做了解。
------------------------------------------------------------------------------
Blog: http://blog.csdn.net/tianlesoftware
网上资源: http://tianlesoftware.download.csdn.net
相关视频:http://blog.csdn.net/tianlesoftware/archive/2009/11/27/4886500.aspx
DBA1 群:62697716(满); DBA2 群:62697977(满)
DBA3 群:62697850 DBA 超级群:63306533;
聊天 群:40132017
--加群需要在备注说明Oracle表空间和数据文件的关系,否则拒绝申请
分享到:
相关推荐
TRUNCATE不会逐个清除用户数据块上的数据,而仅仅重置数据字典和元数据块上的元数据(如存储段头和扩展段图)。也就是说,此时,其基本数据并未被破坏,而是被系统回收、等待被重新分配————因此,要恢复被...
### Oracle用户数据字典以及查询表字段 在Oracle数据库中,数据字典是存储数据库元数据(即关于数据的数据)的特殊集合。这些元数据包括了数据库对象的名称、类型、属性等信息。数据字典对于数据库管理员和开发人员...
Oracle 数据字典是 Oracle 数据库系统的基础组件之一,由表和视图组成,存储有关数据库结构信息的一些数据库对象。数据库字典描述了实际数据是如何组织的,可以象处理其他数据库表或视图一样进行查询,但不能进行...
4. **静态数据字典视图**:为了方便用户访问和管理,Oracle创建了一系列静态数据字典视图,这些视图提供了对数据字典表的访问接口,但通常不允许直接修改。视图根据前缀分为不同类型,如USER_*, DBA_*, ALL_*, 分别...
Oracle 数据字典是由一系列表和视图组成,用于存储关于数据库结构信息的关键数据库对象。这些信息包括但不限于数据库对象的定义、属性以及关系等。数据字典对于理解数据库结构至关重要,同时也为数据库管理提供了...
接着,通过查询数据字典视图ALL_VIEWS,找到包含表列定义信息的视图USER_TAB_COLUMNS,进一步追踪到实际存储这些信息的表SYS.COL$。 然后,我们可以通过ALL_OBJECTS视图查找目标表SCOTT.TEST的OBJECT_ID,以便于...
Oracle 的数据字典分为两部分:数据字典表和数据字典视图。数据字典表用于存储系统内部使用的元数据,而数据字典视图则是基于这些数据字典表构建的,用于提供更加方便的查询接口。 - **查询示例** - 查询表在数据库...
ORACLE 数据字典 ORACLE 数据字典是 Oracle 数据库管理和展现数据库系统信息和状态信息的工具,是一系列基表、基于这些基表而衍生的数据字典视图以及存在于系统内存中的动态性能视图的集合。 数据字典概念:数据...
数据字典在Oracle数据库中扮演着至关重要的角色,它是一系列只读表和视图的集合,用以存储关于数据库结构和配置的重要信息。这些信息对于数据库管理员(DBA)和其他授权用户来说极为宝贵,因为它们提供了对数据库内部...
Oracle数据库是世界上最广泛使用的数据库管理系统之一,其丰富的系统表和视图为DBA(数据库管理员)提供了管理和监控数据库的强大工具。这些表和视图主要分为三类:以`dba_`开头、`user_`开头以及`v$`开头。下面我们...
5. **DELETE_CATALOG_ROLE角色**:在Oracle 8中新增,允许用户删除审计记录表sys.aud$中的条目,简化审计跟踪管理。 6. **SELECT_CATALOG_ROLE和EXECUTE_CATALOG_ROLE角色**: - SELECT_CATALOG_ROLE:拥有查询...
数据字典是Oracle数据库的核心组成部分,它是一组只读的表和视图,由sys用户拥有并维护。数据字典存储了关于数据库的各种系统信息,如对象定义、权限分配、用户信息等。用户通常通过查询数据字典视图来获取所需信息...
Oracle提供数据字典视图来获取表的详细信息: 1. **查询表名和字段名**: ```sql SELECT column_name, data_type FROM user_tab_columns WHERE table_name = 'YOUR_TABLE_NAME'; ``` 或者,如果你有其他...
3. 数据库记录查询中的谓词,并更新数据字典表`SYS.COL_USAGE$`。 4. 再次运行`DBMS_STATS`时,它会检查`SYS.COL_USAGE$`中的信息,以决定是否需要为特定列创建直方图。 #### 11.3 使用直方图时的基数算法...
在Oracle数据库管理工作中,熟练掌握并利用系统提供的数据字典表和动态性能视图(Dynamic Performance Views)对于提高数据库管理效率、确保数据库健康运行至关重要。以下是对给定文件中列出的一些常用表和视图的...
Oracle 数据库通过一系列的系统表来存储有关数据库元数据的信息,这些表对于数据库管理员(DBA)来说极为重要,因为它们提供了数据库内部结构、配置及性能状态的关键信息。下面将详细介绍这些系统表及其作用。 ####...
`DBA_TABLESPACES`和`DBA_DATA_FILES`是Oracle数据库的数据字典视图,用于获取关于表空间和数据文件的信息。 2. **查看表空间物理文件**: - `SELECT TABLESPACE_NAME,FILE_ID,FILE_NAME,ROUND(BYTES / (1024 * ...
在Oracle中,数据字典由一组预定义的表和视图组成,这些表和视图存储在SYS和SYSTEM模式下。数据字典的主要功能包括: 1. **对象信息**:数据字典记录了所有数据库对象,如表、索引、视图、存储过程等的详细信息。...