---恢复内容开始---
索引
与表类似,不仅需要在DD中保存索引的定义,还需要在表空间为它分配实际的存储空间。
将索引和对应的表分别存放在不同硬盘的不同表空间中能够提高查询的速度,因为Oracle能够并行读取不同硬盘的数据,这样可以避免产生I/O冲突
索引分类:
按照索引数据的存储方式:B树索引,位图索引,反向键索引和基于函数的索引;
按照索引列的唯一性可以分为唯一索引和非唯一索引;
按照索引列的个数可以分为单列索引和复合索引
建立索引应该注意以下:
1.索引应该建立在WHERE子句频繁引用列上,如果在大表上频繁地使用某列或某几列作为条件进行索引操作,并且检索行数低于总行数15%,那么应该考虑在这些列上建立索引
2.如果经常需要基于某列或某几列执行排序操作,那么在这些列上建立索引可以加快数据排序速度
3.限制使用索引的个数。索引会影响DML(尤其INSERT,DELETE),因此,规划索引时,必须仔细权衡查询和DML的需求
4.指定索引块空间的使用参数。若insert操作较多,应该考虑设置较大的PCTFREE
5.表和索引部署到相同的表空间,简化表空间的管理;部署到不同的表空间,可以提高访问性能
6.当在大表上建立索引时,使用NOLOGGING,可以最小化重做记录,同时可以节省重做日志空间、降低索引建立时间、提高索引并行建立时间
7.不要在小表上建立索引
8.为了提高多表连接的性能,应该在连接列上建立索引
创建索引
通常是表的所有者建立,其他用户身份建立索引,则要求用户必须有create any index系统权限或 相应表的indext权限
1.建立B树索引(default)--B,balanced
根块:索引顶级块,它包含指向下一级节点的信息
分支块:她包含 指向下一级节点(分支块或叶块)的信息
叶块:通常也称为叶子,它包含索引入口数据,索引入口包含索引列的值和记录对应的物理地址ROWID
如:在scott模式下,为emp表的deptno列创建索引
create index emp_deptno_indext on emp(deptno) pctfree 25 tablespace users;
2.建立位图索引
当列的基数很低时,为其建立B树索引显然不合适。这种情况下,适合使用位图索引
在表中低基数的列上建立位图索引时,系统将表进行一次全面扫描,为遇到的各个取值构建“图表”
如:在HR模式下,在employees的salary列创建位图索引:
create bitmap index emp_salary_bmp
on employees(salary)
tablespace users;
初始化参数create_bitmap_area_size用于指定建立位图索引的位图区大小,默认值是8M,该参数值越大,建立位图索引的速度越快。为了加快创建位图索引的速度,应将参数设置为更大的值。因为该参数是静态参数,所以修改后必须重新启动数据库才能生效。
3、建立反向索引
有这样一种情况,单值递增序列上的索引能够完全利用它的叶子节点,非常紧密地存放数据块,可以有效利用存储空间。然而这种优势是要付出代价的,每条记录都会占据最后的叶子节点,即使删除了先前的节点,也会导致同样的问题。这最终会导致对某一边的叶子节点的大量占用。
而反向索引是一种特殊类型的B树索引,存储结构与常规的B树索引相同。然而,如果用户使用序列在表中输入记录,则反向键索引首先指向每个列键值的字节,然后在反向后的新数据上进行索引。如,用户输入的索引是列为2011,则反向为1102。所以,这种反向会打乱原本递增的序列,使得新数据在值的范围上的分布通常比原来的有序数更均匀。
如:在scott模式下,为表emp的job列创建了反向键索引
create index emp_job_reverse
on emp(job) reverse
tablespace users
/
如果在该列上已经建立了普通的B树索引,那么可以使用alter indext...rebuild 将其重新构建为反向索引
如:在scott模式下,将表emp的deptno列更改为反向键索引(索引名:emp_deptno_index)
alter index emp_deptno_index rebuild reverse;
4.基于函数的索引
在Oracle中,经常会遇到字符大小写敏感的问题,而基于函数的索引只是常规的B树索引,但它存放的数据是由表中的数据应用函数后得到的,而不是直接存放表中的数据本身。
由于SQL语句经常使用小写,所以为了加快数据访问速度,应基于upper函数建立函数索引
如:在scott模式下,为表emp的job列创建函数索引:
create index emp_job_fun
on emp(upper(job));
在创建该函数索引之后,如果在查询条件中包含相同的函数,则系统会利用它来提高查询的执行效率
如果用户在自己的模式中创建基于函数的索引,则必须具有query rewrite系统权限,如果在其他模式中创建索引,必须具有create any index 和global query rewrite
修改索引
一般由所有者完成,如果要以其他用户身份修改索引,用户必须具有alter any index系统权限或在相应表上index对象权限
为表建立索引后,随着对表不断进行更新、插入和删除操作,索引中会产生越来越多的存储碎片,这将对索引的工作效率产生负面影响。这时可以采取两种方式来清楚碎片——重建索引和合并索引
合并索引只是将B树中叶子节点的存储碎片合并在一起,并不会改变索引的物理组织结构。
如:在scott模式下,对索引emp_deptno_index执行合并操作:
---恢复内容结束---
索引
与表类似,不仅需要在DD中保存索引的定义,还需要在表空间为它分配实际的存储空间。
将索引和对应的表分别存放在不同硬盘的不同表空间中能够提高查询的速度,因为Oracle能够并行读取不同硬盘的数据,这样可以避免产生I/O冲突
索引分类:
按照索引数据的存储方式:B树索引,位图索引,反向键索引和基于函数的索引;
按照索引列的唯一性可以分为唯一索引和非唯一索引;
按照索引列的个数可以分为单列索引和复合索引
建立索引应该注意以下:
1.索引应该建立在WHERE子句频繁引用列上,如果在大表上频繁地使用某列或某几列作为条件进行索引操作,并且检索行数低于总行数15%,那么应该考虑在这些列上建立索引
2.如果经常需要基于某列或某几列执行排序操作,那么在这些列上建立索引可以加快数据排序速度
3.限制使用索引的个数。索引会影响DML(尤其INSERT,DELETE),因此,规划索引时,必须仔细权衡查询和DML的需求
4.指定索引块空间的使用参数。若insert操作较多,应该考虑设置较大的PCTFREE
5.表和索引部署到相同的表空间,简化表空间的管理;部署到不同的表空间,可以提高访问性能
6.当在大表上建立索引时,使用NOLOGGING,可以最小化重做记录,同时可以节省重做日志空间、降低索引建立时间、提高索引并行建立时间
7.不要在小表上建立索引
8.为了提高多表连接的性能,应该在连接列上建立索引
创建索引
通常是表的所有者建立,其他用户身份建立索引,则要求用户必须有create any index系统权限或 相应表的indext权限
1.建立B树索引(default)--B,balanced
根块:索引顶级块,它包含指向下一级节点的信息
分支块:她包含 指向下一级节点(分支块或叶块)的信息
叶块:通常也称为叶子,它包含索引入口数据,索引入口包含索引列的值和记录对应的物理地址ROWID
如:在scott模式下,为emp表的deptno列创建索引
create index emp_deptno_indext on emp(deptno) pctfree 25 tablespace users;
2.建立位图索引
当列的基数很低时,为其建立B树索引显然不合适。这种情况下,适合使用位图索引
在表中低基数的列上建立位图索引时,系统将表进行一次全面扫描,为遇到的各个取值构建“图表”
如:在HR模式下,在employees的salary列创建位图索引:
create bitmap index emp_salary_bmp
on employees(salary)
tablespace users;
初始化参数create_bitmap_area_size用于指定建立位图索引的位图区大小,默认值是8M,该参数值越大,建立位图索引的速度越快。为了加快创建位图索引的速度,应将参数设置为更大的值。因为该参数是静态参数,所以修改后必须重新启动数据库才能生效。
3、建立反向索引
有这样一种情况,单值递增序列上的索引能够完全利用它的叶子节点,非常紧密地存放数据块,可以有效利用存储空间。然而这种优势是要付出代价的,每条记录都会占据最后的叶子节点,即使删除了先前的节点,也会导致同样的问题。这最终会导致对某一边的叶子节点的大量占用。
而反向索引是一种特殊类型的B树索引,存储结构与常规的B树索引相同。然而,如果用户使用序列在表中输入记录,则反向键索引首先指向每个列键值的字节,然后在反向后的新数据上进行索引。如,用户输入的索引是列为2011,则反向为1102。所以,这种反向会打乱原本递增的序列,使得新数据在值的范围上的分布通常比原来的有序数更均匀。
如:在scott模式下,为表emp的job列创建了反向键索引
create index emp_job_reverse
on emp(job) reverse
tablespace users
/
如果在该列上已经建立了普通的B树索引,那么可以使用alter indext...rebuild 将其重新构建为反向索引
如:在scott模式下,将表emp的deptno列更改为反向键索引(索引名:emp_deptno_index)
alter index emp_deptno_index rebuild reverse;
4.基于函数的索引
在Oracle中,经常会遇到字符大小写敏感的问题,而基于函数的索引只是常规的B树索引,但它存放的数据是由表中的数据应用函数后得到的,而不是直接存放表中的数据本身。
由于SQL语句经常使用小写,所以为了加快数据访问速度,应基于upper函数建立函数索引
如:在scott模式下,为表emp的job列创建函数索引:
create index emp_job_fun
on emp(upper(job));
在创建该函数索引之后,如果在查询条件中包含相同的函数,则系统会利用它来提高查询的执行效率
如果用户在自己的模式中创建基于函数的索引,则必须具有query rewrite系统权限,如果在其他模式中创建索引,必须具有create any index 和global query rewrite
修改索引
一般由所有者完成,如果要以其他用户身份修改索引,用户必须具有alter any index系统权限或在相应表上index对象权限
为表建立索引后,随着对表不断进行更新、插入和删除操作,索引中会产生越来越多的存储碎片,这将对索引的工作效率产生负面影响。这时可以采取两种方式来清除碎片——重建索引和合并索引
合并索引只是将B树中叶子节点的存储碎片合并在一起,并不会改变索引的物理组织结构。
如:在scott模式下,对索引emp_deptno_index执行合并操作:
alter index emp_deptno_index coalesce deallocate unused;
另一个方法:重建索引 alter index ...rebuild 重建索引不仅可以消除存储碎片,还可以改变索引的全部存储参数设置,以及改变索引的存储表空间。重建索引实际上是在指定的表空间中重新建立一个新的索引,然后再删除原来的索引。
如:alter index emp_deptno_index rebuild tablespace example;
删除索引
其他用户需要drop any index系统权限
需要删除索引的情况:
1.如果移动了表中的数据,导致索引中包含过多的存储碎片,此时需要删除并重建索引
2.通过一段时间的监视,发现很少查询会使用该索引
3.该索引不再需要时应该删除该索引,以释放其所占用的空间
用create index创建的所以,可以通过drop index 删除
如果是Oracle系统自动建立的,则必须禁用或删除该约束本身。另外,在删除一个表时,Oracle也会删除所有与该表有关的索引
在实际应用上,应该根据表的实际情况限制在表中创建的索引数量
显示索引信息
1.显示表的所有索引
dd-dba_indexes:可以显示数据库的所有索引;
dd-all_indexes:可以显示当前用户可访问的所有索引;
dd-user_indexes:可以显示当前用户的索引信息
2.显示索引列
dd--dba_ind_columns:可以显示所有索引的表列信息;
dd--all_ind_columns:可以显示当前用户可以访问的所有索引的表列信息
dd--user_ind_columns:可以显示当前用户索引的表列信息
3.显示索引段位置以及大小
建立索引时,Oracle会为索引分配相应的索引字段,索引数据被存放在索引段中,并且段名与索引名完全相同。
dd--user_segments:可以显示当前用户的索引段的信息
4.显示函数索引
dd-dba_ind_expressions:可以显示数据库所有函数索引所对应的函数或表达式;
dd--user_ind_expressions:可以显示当前用户函数索引所对应的函数或表达式
视图对象
视图是一个虚表,它由存储的查询构成,可以将它的输出看做一个表。视图同真实表一样,也可以包含一系列带有名称的列和行数据。但是视图并不在数据库中存储数据值,其数据值来自定义视图的查询语句所引用的表,数据库只在DD中存储视图的定义
创建视图
其他用户需要有create any view系统权限
--alias:用于指定视图列的别名 在创建视图时,如果不提供视图列别名,Oracle会自动使用子查询的列名或别名;如果视图子查询包含函数或表达式,则必须定义列别名。
1.简单视图
基于单表建立的,不包含任何函数、表达式和分组数据
如:在SCOTT模式下,创建一个查询部门编号为20的视图:
create or replace view emp_view as
select empno,ename,job,deptno
from emp
where deptno=20
/
说明:由于建立视图时,没有提供列名,所以视图的列名分别为empno,ename,job,deptno
用户可以像对待普通表那样,对emp_view select,insert,update,delete等操作
2.建立只读视图
--with read only
这样就只能在该视图上执行select,而禁止执行insert,update,delete
如:在SCOTT模式下,创建一个只读视图,要求该视图可以获得部门编号不等于88的其他所有部门信息
create or replace view emp_view_readonly as
select * from dept where deptno!=88 with read only;
3.复杂视图
是值包含函数、表达式或分组数据的视图,使用复杂视图的主要目的是为了简化查询操作。需要注意的是,当视图子查询中包含函数或表达式时,必须为其定义列别名
如:在SCOTT模式下,创建一个视图,要求能够查询每个部门的工资情况
create or replace view emp_view_complex as
select deptno 部门编号,max(sal) 最高工资,min(sal) 最低工资 ,avg(sal) 平均工资 from emp group by deptno
/
4.连接视图
基于多个表所建立的视图,使用连接视图主要的目的是为了简化连接查询 需要注意的是,建立连接视图时,必须使用where子句中指定有效的连接条件,否则结果就是毫无意义的笛卡尔积:
如:在SCOTT模式下,创建一个dept表和emp表相互关联的视图,并要求该视图只能查询部门编号为20
create or replace view emp_view_union as
select d.dname,d.loc,e.empno,e.ename from emp e,dept d where e.deptno=d.deptno and d.deptno=20
/
管理视图
1.查看视图定义
dd--user_views
--text列显示的就是该视图的select语句
2.修改视图定义
直接使用create or replace as ...直接写新的select语句即可
3.重新编译视图
视图被创建后,如果用户修改了视图所依赖的基本表定义,则该视图会被标记为无效。当用户访问视图时,Oracle会自动重新编译视图。除此之外,可以使用alter view 手动编译
如:手动方式重新编译视图emp_view_union,
alter view emp_view_union compile;
4.删除视图
删除其他用户模式中的视图,要求该用户必须具有drop any view系统权限
如 :drop view emp_view_union;
视图的删除对于基表是没有任何影响的。
同义词对象
同义词是表、索引、视图等模式对象的一个别名。通过模式对象创建同义词,可以隐藏对象的实际名称和所有者信息,或者隐藏分布式数据库中远程对象的设置信息,由此为对象提供一定的安全性保证。与视图、序列一样,同义词只在DD中保存其定义描述,因此同义词也不会占用任何实际的存储空间
在开发数据库应用程序时,应该尽量避免直接引用表、视图或其他数据库对象的名称,而改用这些对象的同义词。这样可以避免当系统管理员对数据库对象做出修改和变动后,必须重新编译应用程序。使用同义词后,即使引用的对象发生变化,也只需要在数据库中对同义词进行修改,而不必对应用程序做任何改动。
Oracle中的同义词分为两种类型:公有同义词和私有同义词。公有同义词被一个特殊的用户组PUBLIC所拥有,数据库中的所有用户都可以使用公有同义词。而私有同义词只被创建它的用户所拥有,只能由该用户以及授权的其他用户使用。
建立公有同义词使用create public synonym .需要用户具有create public synonym系统权限
如:在SYSTEM模式下,为SCOTT模式下的dept表创建一个public同义词:
create public synonym public_dept for scott.dept;
建立私有同义词使用create synonym.如果是当前模式中创建用户具有create synonym权限,而如果在其他模式中创建私有同义词,则数据库用户必须有create any synonym系统权限
如:为dept表创建同义词private_dept:
私有同义词只有当前用户可以直接引用,其他用户在引用时必须带模式名
删除同义词
drop synonym(public)
删除同义词后,同义词的基础对象不会受到任何影响,但是所有引用该同义词的对象将处于INVALID状态
序列对象
是Oracle提供的用于生成一系列唯一数字的数据库对象。序列会自动生成顺序递增的序列号,以实现自动提供唯一的主键值。序列可以在多用户并发环境中使用,并且可以为所有用户生成不重复的顺序数字,而不需要任何额外的I/O开销。
创建序列
用户在其他模式要有create any sequence系统权限
如:在SCOTT模式下 创建一个序列empno_seq
create sequence empno_seq
maxvalue 99999
start with 9000
increment by 100
cache 50
/
使用序列时,需要用到序列的两个伪列nextval 和currval
如:在SCOTT模式下,使用序列empno_seq 为表emp 表的记录提供员工编号:
insert into emp(empno,ename,deptno) values(empno_seq.nextval,'东方',20);
实际上,为表生成主键时,通常是为表创建一个行级触发器,然后在触发器主体中使用序列值替换用户提供的值
管理序列
alter sequence,除了start with,其他参数都可以修改。如果,要修改序列的起始值,则必须先删除序列,然后重建序列
如:在SCOTT模式下,修改序列empno_seq的最大值为100000,序列增量为200,缓存值为100
alter sequence empno_seq
maxvalue 100000
increment by 200
cache 200;
对序列进行修改后,缓存中的序列值将全部丢失。通过查询数据字典user_sequence可以得到序列信息
当序列不再需要时,可以使用
drop sequence empno_seq;