os: centos 7.4
db: oracle 11.2.0.4
oracle数据表三种基本类型:Heap Table、IOT、Cluster。名称分别为 堆表、索引组织表、聚簇表。
通常情况下,堆表是我们的首选项,也是 create table 时的默认选项。
IOT是一种融合数据到索引结构上的数据表类型(另外几篇blog 有介绍)。
聚簇表是最不常用的表类型,cluster 是一种独特的段结构,根据表的关联列,将多个表的关联数据放在一个 cluster 段上,实现快速检索。
Oracle cluster更适合相对静态数据的存储,对于OLTP应用来说,cluster在大部分情况下都不太适用,因为我们都无法预估到数据量的变化,根本无法合理设置cluster的参数。
版本
# cat /etc/centos-release
CentOS Linux release 7.4.1708 (Core)
#
# su - oracle
Last login: Tue Jan 21 03:40:05 CST 2020 on pts/0
$ sqlplus / as sysdba;
SQL*Plus: Release 11.2.0.4.0 Production on Mon Feb 3 10:29:09 2020
Copyright (c) 1982, 2013, Oracle. All rights reserved.
Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
With the Partitioning, Real Application Clusters, Automatic Storage Management, OLAP,
Data Mining and Real Application Testing options
SQL> set lines 300;
SQL> set pages 300;
SQL>
SQL> select * from v$version;
BANNER
--------------------------------------------------------------------------------
Oracle Database 11g Enterprise Edition Release 11.2.0.4.0 - 64bit Production
PL/SQL Release 11.2.0.4.0 - Production
CORE 11.2.0.4.0 Production
TNS for Linux: Version 11.2.0.4.0 - Production
NLSRTL Version 11.2.0.4.0 - Production
SQL>
index cluster
目标用户需要 create cluster 权限
SQL> grant create cluster to scott2;
SQL> create cluster cluster_t0 (c0 varchar2(100)) size 1000 tablespace users;
SQL> select cluster_name, tablespace_name, cluster_type, key_size from dba_clusters where owner='SCOTT2';
CLUSTER_NAME TABLESPACE_NAME CLUST KEY_SIZE
------------------------------ ------------------------------ ----- ----------
CLUSTER_T0 USERS INDEX 1000
SQL> select segment_name,segment_type, extents, header_file, header_block, bytes, blocks from dba_segments where owner='SCOTT2';
SEGMENT_NAME SEGMENT_TYPE EXTENTS HEADER_FILE HEADER_BLOCK BYTES BLOCKS
--------------------------------------------------------------------------------- ------------------ ---------- ----------- ------------ ---------- ----------
CLUSTER_T0 CLUSTER 1 4 1378 65536 8
创建 cluster 的 size 1000 是用于指定 cluster 键大致大小,指定之后,就可以实现空间的预留。
size 的设置需要根据实际情况合理设置。
此时已经创建了一个 cluster segment,用于存放接下来的聚簇表数据。
SQL> create table clu_t0 (
c0 varchar2(100),
c1 varchar2(100),
c2 varchar2(100),
c3 varchar2(100),
constraint pk_clu_t0 primary key (c0)
)
cluster CLUSTER_T0(c0);
;
SQL> insert into clu_t0
select level, dbms_random.string('a',100),dbms_random.string('a',100),dbms_random.string('a',100) from dual connect by level <=10000;
ERROR at line 1:
ORA-02032: clustered tables cannot be used before the cluster index is built
创建表后,插入数据报错,此时还需要创建 cluster index
创建 index
SQL> create index idx_cluster_t0 on cluster CLUSTER_T0;
再次插入数据,成功。
SQL> insert into clu_t0
select level, dbms_random.string('a',100),dbms_random.string('a',100),dbms_random.string('a',100) from dual connect by level <=10000;
SQL> commit;
再创建另外一个表 clu_t1
SQL> create table clu_t1 (
c0 varchar2(100),
c1 varchar2(100),
c2 varchar2(100),
c3 varchar2(100),
constraint pk_clu_t1 primary key (c0)
)
cluster CLUSTER_T0(c0);
;
SQL> insert into clu_t1
select level, dbms_random.string('a',100),dbms_random.string('a',100),dbms_random.string('a',100) from dual connect by level <=5000;
查看一些数据字典
SQL> select cluster_name, tablespace_name, cluster_type, key_size from dba_clusters where owner='SCOTT2';
CLUSTER_NAME TABLESPACE_NAME CLUST KEY_SIZE
------------------------------ ------------------------------ ----- ----------
CLUSTER_T0 USERS INDEX 1000
SQL> select segment_name,segment_type, extents, header_file, header_block, bytes, blocks from dba_segments where owner='SCOTT2';
SEGMENT_NAME SEGMENT_TYPE EXTENTS HEADER_FILE HEADER_BLOCK BYTES BLOCKS
------------------------------ ------------------ ---------- ----------- ------------ ---------- ----------
IDX_CLUSTER_T0 INDEX 6 1 1149568 393216 48
PK_CLU_T0 INDEX 5 1 186872 327680 40
PK_CLU_T1 INDEX 3 1 1149656 196608 24
CLUSTER_T0 CLUSTER 21 4 1378 6291456 768
SQL> set autotrace traceonly;
SQL>
SQL> select t0.*,t1.* from clu_t0 t0,clu_t1 t1 where t0.c0=t1.c0 and t0.c0='998';
no rows selected
Execution Plan
----------------------------------------------------------
Plan hash value: 3166797406
-----------------------------------------------------------------------------------------
| Id | Operation | Name | Rows | Bytes | Cost (%CPU)| Time |
-----------------------------------------------------------------------------------------
| 0 | SELECT STATEMENT | | 1 | 416 | 3 (0)| 00:00:01 |
| 1 | MERGE JOIN CARTESIAN | | 1 | 416 | 3 (0)| 00:00:01 |
| 2 | TABLE ACCESS CLUSTER | CLU_T0 | 1 | 208 | 2 (0)| 00:00:01 |
|* 3 | INDEX UNIQUE SCAN | IDX_CLUSTER_T0 | 1 | | 1 (0)| 00:00:01 |
| 4 | BUFFER SORT | | 1 | 208 | 1 (0)| 00:00:01 |
|* 5 | TABLE ACCESS CLUSTER| CLU_T1 | 1 | 208 | 1 (0)| 00:00:01 |
-----------------------------------------------------------------------------------------
Predicate Information (identified by operation id):
---------------------------------------------------
3 - access("T0"."C0"='998')
5 - filter("T1"."C0"='998')
Note
-----
- dynamic sampling used for this statement (level=2)
Statistics
----------------------------------------------------------
9 recursive calls
0 db block gets
35 consistent gets
0 physical reads
0 redo size
778 bytes sent via SQL*Net to client
509 bytes received via SQL*Net from client
1 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
0 rows processed
参考: