讨论几种数据列Column的特性(上)

 

之前笔者写过一个系列《索引列的usablevisible》(http://space.itpub.net/17203031/viewspace-688135),详细讨论了索引列的usablevisible属性。在11g中,Oracle推出了索引的visibleinvisible属性,用于临时性的屏蔽索引参与优化器过程。

 

在本篇中,我们对应讨论一下column的一些属性,权作为之前系列的续篇。

 

1、环境介绍

 

我们选择Oracle 11gR2进行试验。

 

 

SQL> select * from v$version;

 

BANNER

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

Oracle Database 11g Enterprise Edition Release 11.2.0.1.0 - Production

PL/SQL Release 11.2.0.1.0 - Production

CORE        11.2.0.1.0         Production

 

 

在数据字典dba_tab_cols中,有两个数据列HIDDEN_COLUMNVIRTUAL_COLUMN。本篇主要围绕两个属性进行研究。

 

 

SQL> desc dba_tab_cols;

Name                 Type           Nullable Default Comments                                                            

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

OWNER                VARCHAR2(30)                                                                                        

TABLE_NAME           VARCHAR2(30)                    Table, view or cluster name                                         

(篇幅原因,有省略……

HIDDEN_COLUMN        VARCHAR2(3)    Y                Is this a hidden column?                                            

VIRTUAL_COLUMN       VARCHAR2(3)    Y                Is this a virtual column?                                            

                                          

 

 

2unused column

 

Unused ColumnOracle为了支持快速数据列Column删除提供的一种功能。我们可以通过设置数据列unused的状态,很快地(7×24系统情况下)将数据表的某些列屏蔽组。这个过程中不消耗很多的资源和引起大量的阻塞。

 

Sys用户下有一个数据表T,包括数据列seq_num。我们可以通过set unusable 来将数据列设置为unused

 

 

SQL> show user;

User is "SYS"

 

SQL> alter table t set unused column seq_num;

 

alter table t set unused column seq_num

 

ORA-12988: 无法删除属于 SYS 的表中的列

 

 

Sys用户下的数据表是不能对column进行unused操作的。我们切换到scott用户下,创建数据表t

 

 

SQL> conn scott/tiger@wilson;

Connected to Oracle Database 11g Enterprise Edition Release 11.2.0.1.0

Connected as scott

 

SQL> create table t as select object_id, owner, object_name, last_ddl_time from dba_objects;

Table created

 

SQL> select count(*) from t;

  COUNT(*)

----------

     72779

 

SQL> exec dbms_stats.gather_table_stats(user,'T',cascade => true);

PL/SQL procedure successfully completed

 

 

此时,数据字典中正常数据列信息如下。

 

 

SQL> select column_name, HIDDEN_COLUMN, VIRTUAL_COLUMN, SEGMENT_COLUMN_ID from dba_tab_cols where wner='SCOTT' and table_name='T';

 

COLUMN_NAME           HIDDEN_COLUMN VIRTUAL_COLUMN SEGMENT_COLUMN_ID

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

OBJECT_ID                NO            NO                             1

OWNER                   NO            NO                             2

OBJECT_NAME             NO            NO                             3

LAST_DDL_TIME            NO            NO                             4

 

 

此时,四个数据列都是正常的。使用set unusable属性。

 

 

SQL> alter table t set unused column owner;

 

Table altered

 

SQL> select column_name, HIDDEN_COLUMN, VIRTUAL_COLUMN, SEGMENT_COLUMN_ID from dba_tab_cols where wner='SCOTT' and table_name='T';

 

COLUMN_NAME                    HIDDEN_COLUMN VIRTUAL_COLUMN SEGMENT_COLUMN_ID

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

OBJECT_ID                      NO            NO                             1

SYS_C00002_13080423:42:23$     YES           NO                             2

OBJECT_NAME                    NO            NO                             3

LAST_DDL_TIME                  NO            NO                             4

 

 

owner列进行unused处理之后,我们发现数据字典中,原有的字段被修改为一个系统内部名称“SYS_C00002_13080423:42:23$”。字段的hindden_column取值为Yes,说明不再显示出来。

 

注意:对一个字段进行unused属性设置,是一个标记性的动作。对应的数据表段结构没有进行收缩动作,对应的空间也不会回收。重要的是,对一个字段进行unused处理过程持续时间很短,远低于drop一个数据大表数据列的过程。

 

而且,修改的列名中,有很强烈的时间信息,也就反映了进行操作的时间点。

 

 

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

 

TO_CHAR(SYSDATE,'YYYY-MM-DDHH2

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

2013-08-04 23:52:26

 

 

被设置为unused之后,字段就不会出现在select *desc列表中,Oracle原则上也不会承认这个字段了。

 

 

SQL> desc t;

Name          Type          Nullable Default Comments

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

OBJECT_ID     NUMBER        Y                        

OBJECT_NAME   VARCHAR2(128) Y                        

LAST_DDL_TIME DATE          Y                         

 

SQL> col object_name for a10;

SQL> select * from t where rownum<5;

 

 OBJECT_ID OBJECT_NAM LAST_DDL_TIME

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

        20 ICOL$      13-八月-09 23

        46 I_USER1    13-八月-09 23

        28 CON$       13-八月-09 23

        15 UNDO$      13-八月-09 23

 

SQL> insert into t (owner) values ('kk');

 

insert into t (owner) values ('kk')

 

ORA-00904: "OWNER": 标识符无效

 

 

注意,在Oracle Index里面,如果一个索引状态是unusable了,表示该索引需要重建rebuild操作。但是数据字段如果unused,目前是没有方法将其逆转过来的。

 

 

SQL> alter table t set used column owner;

 

alter table t set used column owner

 

ORA-02000: 缺失 UNUSED 关键字

 

 

设置成unusedcolumn信息理论上还存在在数据段segment结构里面。我们可以选择一个“合适”的时间进行删除。

 

 

SQL> alter table t drop unused columns;

(持续时间长)

Table altered

 

 

SQL> desc t;

Name          Type          Nullable Default Comments

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

OBJECT_ID     NUMBER        Y                        

OBJECT_NAME   VARCHAR2(128) Y                        

LAST_DDL_TIME DATE          Y                         

 

SQL> select column_name, HIDDEN_COLUMN, VIRTUAL_COLUMN, SEGMENT_COLUMN_ID from dba_tab_cols where wner='SCOTT' and table_name='T';

 

COLUMN_NAME                    HIDDEN_COLUMN VIRTUAL_COLUMN SEGMENT_COLUMN_ID

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

OBJECT_ID                      NO            NO                             1

OBJECT_NAME                    NO            NO                             2

LAST_DDL_TIME                  NO            NO                             3

 

 

Drop unused columns可以一次性的将数据表上面所有的unused列删除掉。这个过程是真正进行的删除,如果数据表比较大的话,这个操作持续时间还是比较长的。

 

最后我们聊聊unused column的实际意义。应该说,这个功能对于开发阶段而言,没有任何意义。对于投产上线过程和升级过程的DBA运维工作,有一定作用。

 

在进行投产上线的时候,比如系统新版本需要删除某些大表的字段。如果系统是7×24小时运行,投产上线阶段给定的时间窗口不够,直接删除字段引起的阻塞风险和时间成本可能是运维单位不能承受的。Unused column提供了一种可能,就是快速的将数据表字段屏蔽住,减少这种阻塞时间。段级别的删除,可以调整到系统正式的维护窗口中一点点的去完成。

 

下面我们会继续讨论几种column特性。

 

来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/17203031/viewspace-767825/,如需转载,请注明出处,否则将追究法律责任。

转载于:http://blog.itpub.net/17203031/viewspace-767825/

你可能感兴趣的:(讨论几种数据列Column的特性(上))