设为首页 收藏本站
查看: 1725|回复: 0

[经验分享] 《Oracle编程艺术》学习笔记(26)-索引聚簇表

[复制链接]
YunVN网友  发表于 2016-8-15 06:46:48 |阅读模式
聚簇(cluster)是指:如果一组表有一些共同的列,则将这样一组表存储在相同的数据库块中;聚簇还表示把相关的数据存储在同一个块上。
聚簇并不是有序地存储数据(这是IOT的工作),它是按每个键以聚簇方式存储数据,但数据存储在堆中。利用聚簇,一个块可能包含多个表的数据。聚簇也可以用于单个表,可以按某个列将数据分组存储。
SQL Server 中的聚簇索引(clustered index)则要求行按索引键有序的方式存储,这类似于前面所述的IOT。  例如,有部门和员工2张表,将部门号作为聚簇列,建立聚簇表。这样部门号10的部门数据和包括的所有员工数据都存储在同一个块上,如果放不下,则串链其他块。
但是部门在磁盘上的存储并不是有序的,部门100可能挨在部门1旁边,而与部门101和99离得很远。
  创建索引聚簇表(index clustered table)的步骤:
1)创建聚簇
create cluster emp_dep_cluster (depno number(2)) size 2048;  SIZE选项告诉Oracle与每个聚簇键值关联大约2048字节的数据,Oracle会使用这个参数来计算每个块最多能放下多少个聚簇键。假设块大小为8KB,Oracle会在每个数据库块上放上最多3个聚簇键。
对于聚簇来说,SIZE是最重要的参数,这是对聚簇空间利用率影响最大的因素。如果把这个SIZE设置得太高,那么每个块上的键就会很少,会不必要地使用更多的空间。如果设置得太低,又会导致数据过分串链。
对象的存储定义参数(PCTFREE、PCTUSED、INITRANS等)与 CLUSTER相关,而不是与表相关。因为聚簇中会有多个表,而且它们在同一个块上。
  2)创建聚簇键索引
create index emp_dep_cluster_idx on cluster emp_dep_cluster;  也可以在聚簇中创建完表格后再创建,但是必须在插入数据前创建,否则会得到下述错误。
ORA-02032: clustered tables cannot be used before the cluster index is built
聚簇索引就像是一个常规的索引,使用和常规同样的的存储参数,也可以存储在另一个表空间中,也可以在多列上建立。
注意,CREATE INDEX语句中,并没有指定列的一个列表,索引列可以由CLUSTER定义本身得出。
  3)创建表格
create table department (depno number(2) primary key, depname varchar2(20))cluster emp_dep_cluster(depno);create table employee (empno number primary key, empname varchar2(20), depno number(2) references department(depno))cluster emp_dep_cluster(depno);  
需要使用CLUSTER关键字来指定基表的哪个列会映射到聚簇本身的聚簇键。
聚簇中的表使用创建聚簇时生成的聚簇段,不会有诸如TABLESPACE、PCTFREE等段属性。
  在表格中插入一些数据,然后观察在磁盘上的存放。
tony@ORA11GR2> select rowid, dbms_rowid.rowid_block_number(rowid) block, depno from department;ROWID                   BLOCK      DEPNO------------------ ---------- ----------AAASIEAAEAAADN0AAA      13172         10AAASIEAAEAAADN0AAB      13172         20AAASIEAAEAAADN0AAC      13172         30AAASIEAAEAAADN1AAA      13173         40tony@ORA11GR2> select rowid, dbms_rowid.rowid_block_number(rowid) block, empno, depno from employee;ROWID                   BLOCK      EMPNO      DEPNO------------------ ---------- ---------- ----------AAASIEAAEAAADN0AAA      13172       7369         20AAASIEAAEAAADN0AAB      13172       7566         20AAASIEAAEAAADN0AAC      13172       7654         30AAASIEAAEAAADN0AAD      13172       7698         30AAASIEAAEAAADN0AAE      13172       7782         10AAASIEAAEAAADN0AAF      13172       7788         20AAASIEAAEAAADN0AAG      13172       7839         10AAASIEAAEAAADN0AAH      13172       7844         30AAASIEAAEAAADN0AAI      13172       7876         20AAASIEAAEAAADN0AAJ      13172       7902         20AAASIEAAEAAADN0AAK      13172       7934         10AAASIEAAEAAADN1AAA      13173       7499         40AAASIEAAEAAADN1AAB      13173       7521         40AAASIEAAEAAADN1AAC      13173       7900         40tony@ORA11GR2> show parameter block_sizeNAME                                 TYPE                   VALUE------------------------------------ ---------------------- ------------------------------db_block_size                        integer                8192  
可以看到:
1)由于我们设置了聚簇的SIZE参数为2048,块大小为8K,所以1个块上最多放3个唯一的聚簇键。因此DEPNO为40的数据放到了另外1个块上。
2)DEPARTMENT和EMPLOYEE中的ROWID有重复。说明ROWID只是在表中唯一。
  什么时候适合是用索引聚簇表:
· 数据主要用于读(这并不表示“从来不写”;聚簇表完全可以修改),而且要通过索引来读(可以是聚簇键索引,也可以是聚簇表上的其他索引)
· 需要频繁地把逻辑上相关而且总是一起使用的表信息联结在一起

Oracle数据字典就大量使用了聚簇表。例如
select cluster_name, table_name from dba_tables where cluster_name='C_OBJ#';
C_OBJ#聚簇中存储的主要是与列相关的信息,所以关于表或索引列集的所有信息都物理地存储在同一个块上。Oracle解析一个查询时,它希望访问所引用的表中所有列的数据。如果这些数据都在一个块上,通常就能很容易地得到。
  什么时候不适合使用聚簇表:
· 如果预料到聚簇中的表会大量修改。索引聚簇会对DML的性能产生某种负面影响。
· 如果需要对聚簇中的某个表执行全表扫描。全表扫描不只是读取了需要的某个表中的数据,还读取了其它的多个表中的数据,全表扫描耗时更久。
· 如果需要频繁地TRUNCATE和加载表。聚簇中的表不能截除,因为聚簇在一个块上存储了多个表,必须删除聚簇表中的行。
· 如果需要对表进行分区。聚簇中的表不能被分区。聚簇本身也不能被分区。

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-257793-1-1.html 上篇帖子: Oracle虚拟私有数据库(VPD)概述及简单举例 下篇帖子: 如何有效地利用oracle的数据字典
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表