Oracle 唯一 约束(unique constraint) 与 索引(index) 关系说明

一. 官网对Unique Constraints说明

http://download.oracle.com/docs/cd/E11882_01/server.112/e16508/datainte.htm#CNCPT1642

uniquekey constraint requires that every value in a column or set of columns beunique. No rows of a table may have duplicate values in a column (the uniquekey) or set of columns (the composite unique key) with a unique key constraint.

Note:

Theterm key refers only to the columns defined in the integrity constraint. Because the database enforces a unique constraint byimplicitly creating or reusing an index on the key columns, the term uniquekey is sometimes incorrectly used as a synonym for unique key constraint orunique index.

--数据库在创建unique constraint的同时,强制创建或者重用列上的索引。如果之前列上没有索引,那么强制创建的索引是unique index,如果列上已经存在索引,就重用之前的索引。

Uniquekey constraints are appropriate for any column where duplicate values are notallowed. Unique constraints differ from primary keyconstraints, whose purpose is to identify each table row uniquely, andtypically contain values that have no significance other than being unique.Examples of unique keys include:

(1)A customer phone number, where the primary key is the customernumber

(2)A department name, where the primary key is the department number

Asshown in Example2-1, a unique key constraint exists on the email column of the hr.employeestable. The relevant part of the statement is as follows:

CREATE TABLE employees    ( ...

,email          VARCHAR2(25)

CONSTRAINT   emp_email_nn  NOT NULL ...

,CONSTRAINT     emp_email_uk  UNIQUE (email) ... );

Theemp_email_uk constraint ensures that no two employees have the same emailaddress, as shown inExample5-1.

Example 5-1 Unique Constraint

SQL> SELECT employee_id, last_name,email FROM employees WHERE email = ‘PFAY‘;

EMPLOYEE_ID LAST_NAME                 EMAIL

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

202 Fay                       PFAY

SQL> INSERT INTO employees (employee_id,last_name, email, hire_date, job_id)

1  VALUES(999,‘Fay‘,‘PFAY‘,SYSDATE,‘ST_CLERK‘);

.

.

.

ERROR at line 1:

ORA-00001:unique constraint (HR.EMP_EMAIL_UK) violated

Unless a NOT NULLconstraint is also defined, a null always satisfies a unique key constraint. Thus,columns with both unique key constraints and NOT NULL constraints are typical.This combination forces the user to enter values in the unique key andeliminates the possibility that new row data conflicts with existing row data.

Note:

Because of the searchmechanism for unique key constraints on multiple columns, you cannot haveidentical values in the non-null columns of a partially null composite uniquekey constraint.

二. 相关测试

2.1 测试unique index 和 uniqueconstraint

[email protected](rac2)> create table ut(idnumber,phone varchar2(15),name varchar2(15));

Table created.

[email protected](rac2)> insert into utvalues(1,‘13888888888‘,‘dave‘);

1 row created.

[email protected](rac2)> insert into utvalues(1,‘13888888888‘,‘dave‘);

1 row created.

[email protected](rac2)> insert into utvalues(2,‘13899999999‘,‘dba‘);

1 row created.

[email protected](rac2)> commit;

Commit complete.

--在phone 字段上,我们创建uniqueconstraint

[email protected](rac2)> alter table ut addconstraint uc_phone unique(phone);

alter table ut add constraint uc_phoneunique(phone)

*

ERROR at line 1:

ORA-02299: cannot validate (SYS.UC_PHONE) -duplicate keys found

--这里报错,因为我们在插入数据的时候,有重复值,先删除掉重复值

[email protected](rac2)> select * from ut;

ID PHONE           NAME

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

1 13888888888     dave

2 13899999999     dba

1 13888888888     dave

[email protected](rac2)> delete from ut whererownum=1;

1 row deleted.

[email protected](rac2)> commit;

Commit complete.

[email protected](rac2)> select * from ut;

ID PHONE           NAME

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

2 13899999999     dba

1 13888888888     dave

--唯一性约束创建成功

[email protected](rac2)> alter table ut addconstraint uc_phone unique(phone);

Table altered.

--查看约束

[email protected](rac2)> selectconstraint_name,constraint_type,table_name,index_owner,index_name fromuser_constraints where table_name = ‘UT‘;

CONSTRAINT_NAME C TABLE_NAME  INDEX_OWNER  INDEX_NAME

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

UC_PHONE        U UT            SYS           UC_PHONE

--Oracle 自动创建了索引并关联到约束, 索引名和约束名是相同的。

--验证下索引

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

INDEX_NAME    INDEX_TYPE    UNIQUENES GENERATED

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

UC_PHONE      NORMAL        UNIQUE    N

--我们并没有创建索引,而是在创建unique constraint时,oracle 强制创建了uniqueindex。

--现在我们drop index 看看

[email protected](rac2)> drop index uc_phone;

drop index uc_phone

*

ERROR at line 1:

ORA-02429: cannot drop index used forenforcement of unique/primary key

--这里报错,不能删除unique/primary key 上的索引。在这种情况下,我们只有先删除约束。

[email protected](rac2)> alter table ut dropconstraint uc_phone;

Table altered.

[email protected](rac2)> drop index uc_phone;

drop index uc_phone

*

ERROR at line 1:

ORA-01418: specified index does not exist

--再次drop 索引时,提示索引已经不存在,说明已经在删除约束的同时,把索引删掉了。

[email protected](rac2)> selectconstraint_name,constraint_type,table_name,index_owner,index_name fromuser_constraints where table_name = ‘UT‘;

no rows selected

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

no rows selected

结论:

当约束列上没有索引时,在创建unique constraint 时,oracle 会自动创建unique index,并且该索引不能删除,当删除unique constraint 时,unique index 会自动删除。

2.2 测试unique constraint 和non-unique index

--现在字段phone上创建B-Tree索引

[email protected](rac2)> create indexidx_ut_phone on ut(phone);

Index created.

--查看索引

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

INDEX_NAME    INDEX_TYPE    UNIQUENES GENERATED

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

IDX_UT_PHONE  NORMAL       NONUNIQUE N

--创建unique constraint

[email protected](rac2)>  alter table ut add constraint uc_phoneunique(phone);

Table altered.

--查看约束和索引信息

[email protected](rac2)> selectconstraint_name,constraint_type,table_name,index_owner,index_name fromuser_constraints where table_name = ‘UT‘;

CONSTRAINT_NAME C TABLE_NAME   INDEX_OWNER  INDEX_NAME

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

UC_PHONE        U UT            SYS           IDX_UT_PHONE

--这里重用了已经存在的索引

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

INDEX_NAME    INDEX_TYPE    UNIQUENES GENERATED

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

IDX_UT_PHONE  NORMAL       NONUNIQUE N

--删除索引

[email protected](rac2)> drop indexIDX_UT_PHONE;

drop index IDX_UT_PHONE

*

ERROR at line 1:

ORA-02429: cannot drop index used forenforcement of unique/primary key

--这个提示和之前的一样,我们先删除约束,在来查看

[email protected](rac2)> alter table ut dropconstraint uc_phone;

Table altered.

[email protected](rac2)> select constraint_name,constraint_type,table_name,index_owner,index_namefrom user_constraints where table_name = ‘UT‘;

no rows selected

--这里约束已经删除掉了。

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

INDEX_NAME    INDEX_TYPE    UNIQUENES GENERATED

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

IDX_UT_PHONE  NORMAL       NONUNIQUE N

--但是我们的索引并在删除约束时删除掉

--在手工删除索引,成功

[email protected](rac2)> drop indexIDX_UT_PHONE;

Index dropped.

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

no rows selected

--重新把约束和索引加上,然后一次删除

[email protected](rac2)> create indexidx_ut_phone on ut(phone);

Index created.

[email protected](rac2)> alter table ut addconstraint uc_phone unique(phone);

Table altered.

[email protected](rac2)> selectconstraint_name,constraint_type,table_name,index_owner,index_name fromuser_constraints where table_name = ‘UT‘;

CONSTRAINT_NAME C TABLE_NAME    INDEX_OWNER   INDEX_NAME

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

UC_PHONE        U UT            SYS           IDX_UT_PHONE

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

INDEX_NAME    INDEX_TYPE    UNIQUENES GENERATED

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

IDX_UT_PHONE  NORMAL       NONUNIQUE N

[email protected](rac2)> alter table ut drop constraint uc_phone drop index;

Table altered.

[email protected](rac2)> selectconstraint_name,constraint_type,table_name,index_owner,index_name fromuser_constraints where table_name = ‘UT‘;

no rows selected

[email protected](rac2)> selectindex_name,index_type,uniqueness,generated from user_indexes wheretable_name=‘UT‘;

no rows selected

--索引和约束一次删除

小结:

当我们的列上有索引时,在创建unique constraint时,Oracle 会重用之前的索引,并且不会改变索引的类型,在第一个测试里,Oracle 自动创建的索引是unique index。

当我们删除约束时,关联的索引不会自动删除。 这个问题的MOS 上有说明。 参考MOS [ID309821.1]。

我们可以分两步,先删除约束,在删除索引。 MOS 提供了方法,就是在删除约束时,加上drop index,这样就能一次搞定。

SQL>altertable ut drop constraint uc_phone drop index;

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

Blog: http://blog.csdn.net/tianlesoftware

Email: [email protected]

DBA1 群:62697716(满);   DBA2 群:62697977(满)  DBA3 群:62697850(满)

DBA 超级群:63306533(满);  DBA4 群: 83829929  DBA5群: 142216823

DBA6 群:158654907  聊天 群:40132017   聊天2群:69087192

--加群需要在备注说明Oracle表空间和数据文件的关系,否则拒绝申请

原文出处:

http://blog.csdn.net/tianlesoftware/article/details/6604098

原文地址:https://www.cnblogs.com/pejsidney/p/10316040.html

时间: 2024-11-10 13:52:53

Oracle 唯一 约束(unique constraint) 与 索引(index) 关系说明的相关文章

NULL和唯一约束UNIQUE的对应关系

NULL和唯一约束UNIQUE的对应关系 在数据库中,NULL表示列值为空.唯一约束UNIQUE规定指定列的值必须是唯一的,值和值之间都不能相同.这个时候,就出现一个问题,NULL和NULL算是相同,还是不同.由于SQL语法没有明确规定,所以各个数据库厂商的处理方式不同. (1)PostgreSQL和Oracle认为NULL表示没有指定数据,所以数据有多种可能,所以UNIQUE约束列中允许存在任意个NULL. (2)Informix和SQL Server认为NULL就表示空,是一种唯一的状态.所

Oracle之唯一性约束(UNIQUE Constraint)使用方法具体解释

Oracle | PL/SQL唯一索引(Unique Constraint)使用方法 1 目标 用演示样例演示怎样创建.删除.禁用和使用唯一性约束. 2 什么是唯一性约束? 唯一性约束指表中一个字段或者多个字段联合起来可以唯一标识一条记录的约束. 联合字段中,可以包括空值. 注:在Oracle中,唯一性约束最多能够有32列. 唯一性约束能够在创建表时或使用ALTER TABLE语句创建. 3 唯一性约束和主键的差别 主键(Primary Key):全部组成主键的列都不能包括空值. 唯一性约束(U

Oracle之唯一性约束(UNIQUE Constraint)用法详解

Oracle | PL/SQL唯一索引(Unique Constraint)用法 1 目标 用示例演示如何创建.删除.禁用和使用唯一性约束. 2 什么是唯一性约束? 唯一性约束指表中一个字段或者多个字段联合起来能够唯一标识一条记录的约束.联合字段中,可以包含空值. 注:在Oracle中,唯一性约束最多可以有32列. 唯一性约束可以在创建表时或使用ALTER TABLE语句创建. 3 唯一性约束和主键的区别 主键(Primary Key):所有组成主键的列都不能包含空值. 唯一性约束(Unique

oracle的约束隐式创建索引和先索引后约束的区别

两种情况:1.对于创建约束时隐式创建的索引,在做删除操作的时候: 9i~11g都会连带删除该索引 2.对于先创建索引,再创建约束(使用到此索引)这种情况:9i版本:需要区分索引是否唯一: 如果索引是唯一的,则删除约束的时候,会连带删除索引:如果非唯一的,则不会删除索引.10g以后版本,包括11g:无论索引是否唯一,都只是删除约束,索引不会删除. 参考metalink文档:309821.1 实验验证下$ ss SQL*Plus: Release 11.2.0.3.0 Production on W

Oracle索引总结(七)- Oracle唯一索引、普通索引及约束的关系

Oracle唯一索引.普通索引及约束的关系 在总结索引扫描类型前(不同于前面总结的五大类索引类型,索引类型主要是索引类别的划分,而索引扫描类型是索引在进行索引扫描时的具体方法),需要了解唯一索引.非唯一索引(普通索引)以及约束的关系.这是因为对于索引扫描类型的具体探讨上,需要根据"唯一索引"."非唯一索引(普通索引)"以及"约束",这三个概念的具体情况,进行具体说明,因此优先进行总结. 1.唯一索引与普通索引的概述 对于索引,如b-tree索引,

mysql,sql server,oracle 唯一索引字段是否允许出现多个 null 值?

最近一个项目,涉及到sql server 2008,因为业务需求,希望建立一个唯一索引,但是发现在sql server中,唯一索引字段不能出现多个null值,下面是报错信息: CREATE UNIQUE NONCLUSTERED INDEX weixin_openid_ui ON Users(weixin_openid); 因为发现对象名称 'dbo.Users' 和索引名称 'weixin_openid_ui' 有重复的键,所以 CREATE UNIQUE INDEX 语句终止.重复的键值为

MySql -- UNIQUE唯一约束

3.UNIQUE 约束 约束唯一标识数据库表中的每条记录. 创建一张测试表: CREATE TABLE `test`.`info`( `id` INT(11) UNSIGNED NOT NULL AUTO_INCREMENT, `idCard` VARCHAR(18) UNIQUE NOT NULL, -- 直接在字段上添加唯一约束 `mobile` VARCHAR(11), PRIMARY KEY (`id`) ) ENGINE=INNODB CHARSET=utf8 COLLATE=utf8

oracle数据库表约束、视图、索引—该记录为本人以前微博的文章

一.Oracle 数据库常用操作续关于创建表时创建约束1.创建表的时候增加约束----约束是定义表中的数据应该遵循的规则或者满足的条件----约束是建立在列上的,让某一列或者某几列数据之间有约束----约束可以在创建的表的同时创建约束,也可以在创建表之后再创建约束----约束分为表级约束和列级约束,定义的方式不同,但是效果是相同的----列级约束:列名  数据类型 [default 默认值] [列级约束1  列级约束2--]----表级约束:constraint 约束名称 约束类型(列名)---

索引 index

数据库访问性能优化 特别说明: 1.  本文只是面对数据库应用开发的程序员,不适合专业DBA,DBA在数据库性能优化方面需要了解更多的知识: 2.  本文许多示例及概念是基于Oracle数据库描述,对于其它关系型数据库也可以参考,但许多观点不适合于KV数据库或内存数据库或者是基于SSD技术的数据库: 3.  本文未深入数据库优化中最核心的执行计划分析技术. 读者对像: 开发人员:如果你是做数据库开发,那本文的内容非常适合,因为本文是从程序员的角度来谈数据库性能优化. 架构师:如果你已经是数据库应