從Oracle9iR2 開始,ORACLE提供了表/表空間壓縮技術,以減少磁盤開銷,節省空間,並在某些情況下提高查詢性能。
表壓縮是如何工作的在Orcle9i第2版中,表壓縮特性通過刪除在數據庫表中發現的重複數據值來節省空間。壓縮是在數據庫的數據塊級別上進行的。當確定一個表要被壓縮後,數據庫便在每一個數據庫數據塊中保留空間,以便儲存在該數據塊中的多個位置上出現的數據的單一拷貝。這一被保留的空間被稱作符號表(symbol table)。被標識爲要進行壓縮的數據只存儲在該符號表中,而不是在數據庫行本身內。當在一個數據庫行中出現被標識爲要壓縮的數據時,該行在該符號表中存儲一個指向相關數據的指針,而不是數據本身。節約空間是通過刪除表中數據值的冗餘拷貝而實現的。
1.表級別
1.1 創建一個壓縮表:創建表時使用COMPRESS關鍵字,COMPRESS關鍵字指示Oracle數據庫儘可能以壓縮的格式存儲該表中的行。
create table test compress as select * from dba_objects where 1=2;
create table test (id number,name varchar2(20),time date) compress;
1.2 修改現有表爲壓縮表:
alter table test compress;
取消表的壓縮:
alter table test nocompress;
1.3 確定表是否被壓縮:確定一個表是否使用了壓縮,查詢user_tables,compression字段表明表是否被壓縮
select table_name,compression from user_tables where table_name not like 'BIN%';
SQL> select table_name,compression from user_tables where table_name not like 'BIN%'; TABLE_NAME COMPRESS ----------------------------- -------- CLASSES ENABLED ROOMS ENABLED STUDENTS DISABLED MAJOR_STATS DISABLED
2.表空間級別
2.1創建表壓縮空間
create tablespace TEST datafile '/export/home/oracle/ora10g/oradata/test/test.dbf' size 10M default compress
與其他存儲參數類似,COMPRESS屬性也具有一些繼承特性。當在一個表空間中創建一個表時,它從該表空間繼承COMPRESS屬性。
2.2.使現有表空間轉換爲壓縮表空間
alter tablespace test default compress;
alter tablespace test default nocompress;
2.3.確定是否已經利用compress對一個表空間進行了定義,可查詢user_tablespaces數據字典視圖並查看def_tab_compression列
select tablespace_name,def_tab_compression from user_tablespaces;
SQL> select tablespace_name,def_tab_compression from user_tablespaces; TABLESPACE DEF_TAB_ ---------- -------- USERS DISABLED TEST DISABLED UNDOTBS01 DISABLED STATPACK DISABLED
3.向一個壓縮的表中加載數據
注:當像上面那樣指定compress時,其它表中(表空間)的數據並沒有壓縮,它只是修改了數據字典的設置;只有在向一個表中加裁/插入數據時,纔會壓縮數據.
只有在使用下面4種方法時,表中的數據纔會被壓縮存放:
(1).直接路徑的 sql*load
(2).帶有/*+ append*/的 insert語句
(3).create table .. as select..
(4).並行insert
4.壓縮一個已經存在但並未壓縮的表
使用alter table .. move compress使一個已存在但未壓縮的錶轉換爲壓縮表.
alter table tmp_test move compress;
同樣,也可以使用alter table.. move nocompress來解壓一個已經壓縮的表:
alter table tmp_test move nocompress;
5.壓縮一個物化視圖
使用用於壓縮表的類似方式來壓縮物化視圖。
基於多個表的聯接生成的物化視圖通常很適於壓縮,因爲它們通常擁有大量的重複數據項。
create materialized view mv_tmp_test
compress
as
select a.phone,b.create_time from tmp_test a,recv_stat b
where a.id=b.id;
可以使用ALTER MATERIALIZED VIEW命令來改變一個物化視圖的壓縮屬性。
當你使用此命令時,請注意通常是在下一次刷新該物化視圖時纔會進行實際的壓縮。
alter materialized view mv_temp_test compress;
6.壓縮一個已分區的表
在對已分區的表應用壓縮時,可以有很多種選擇。你可以在表級別上應用壓縮,也可以在分區級別上應用壓縮。
你可以利用ALTER TABLE ...MOVE PARTITION命令對此分區進行壓縮
alter table tmp_test move partition create_200606 compress;
要找出一個表中的哪些分區被壓縮了,可以查詢數據字典視圖USER_TAB_PARTITIONS
SELECT TABLE_NAME, PARTITION_NAME,COMPRESSION FROM USER_TAB_PARTITIONS;
7.壓縮表的性能開銷
一個壓縮的表可以存儲在更少的數據塊中,從而節省了儲存空間,而使用更少的數據塊也意味着性能的提高。 在一個I/O受到一定限制的環境中對一個壓縮的表進行查詢通常可以更快速地完成,因爲他們需要閱讀的數據庫數據塊要少得多。
使用sql*load加載100萬數據:
表名 行數 路徑 是否是壓縮的 消耗的時間
test_nocom 1000000 直接 非壓縮的 00:00:21.12
test_comp 1000000 直接 壓縮的 00:00:47.77
由此可以看出,向壓縮表中加入數據的時間是正常表的一倍.加載壓縮的表所需要的額外時間來自於在數據加載過程中所執行的壓縮操作。