SQL中的唯一约束用于检查子查询的结果中是否有重复的元组。它返回一个布尔值,指示是否存在重复元组。仅当子查询没有重复元组时,唯一构造才返回true,否则返回false。

重点:

  • 在空子查询上求值为true。
  • 仅当存在唯一元组作为子查询的输出时才返回true(如果两个元组的任何属性的值不同,则两个元组是唯一的)。
  • 如果子查询具有两个重复行,并且至少有一个属性为NULL,则返回true。

句法:

SELECT table.ID
从表
WHERE UNIQUE(SELECT table2.ID
              从table2
              table.ID = table2.ID);

注意:在执行期间,首先评估外部查询以获取table.ID。在此之后,处理内部子查询,其产生包含内部查询的输出的新关系,使得table.ID == table2.ID。如果新关系中的每一行都是唯一的,则unique返回true,并将相应的table.ID作为元组添加到生成的输出关系中。但是,如果新关系中的每一行都不唯一,则unique的计算结果为false,并且相应的table.ID不会添加到输出关系中。

当且仅当存在两个元组t1和t2使得t1 = t2时,应用于子查询的唯一返回false。它将t1和t2视为两个不同的元组,当unique应用于包含t1和t2的子查询时,使得t1 = t2并且这些元组的至少一个属性包含NULL值。在这种情况下,唯一谓词的计算结果为true。这是因为,SQL中的NULL值被视为未知值,因此,两个NULL值被视为不同。

注意:没有UNIQUE子句的SQL语句也可以写成:

SELECT table.ID
从表
WHERE 1 <=(SELECT count(table2.ID)
              从table2
              table.ID = table2.ID);

查询

示例1:查找2017年最多教授一门课程的所有教师。
教师 关系:

员工ID 名称 COURSEID
77505 艾伦 SC110 2017年
77815 CSE774 2017年
85019 工匠 EE457 2017年
92701 山姆 PYS504 2017年
60215 哈罗德 HSS103 2016
77505 艾伦 BIO775 2017年
92701 山姆 ECO980 2017年

SQL查询:

选择I.EMPLOYEEID,I.NAME
来自导师,我
WHERE UNIQUE(选择Inst.EMPLOYEEID
              FROM Instructor as Inst
              在哪里I.EMPLOYEEID = Inst.EMPLOYEEID
                          和Inst.YEAR = 2017);

输出:

员工ID 名称
77815
85019 工匠

说明:在讲师关系中,只有教师Will和Smith在2017年教授单个课程。对应于这些教师的子查询只包含一个元组,因此对应于这些教师的唯一子句评估为true,从而产生这两个教师在输出关系中。


示例2:查找计算机科学系的所有课程,该课程只有一名教师分配给该课程。
课程关系:

COURSEID 课程 INSTRUCTORID
CSE505 计算机网络 计算机科学 11071
CSE245 操作系统 计算机科学 74505
CSE101 程序设计 计算机科学 12715
HSS505 心理学 社会科学 85017
EE475 信号与系统 电动 22150
CSE314 DBMS 计算机科学 44704
CSE505 计算机网络 计算机科学 11747
CSE314 DBMS 计算机科学 44715

SQL查询:

SELECT C.COURSEID,C.NAME
从课程C
WHERE UNIQUE(选择T.INSTRUCTORID
              从课程作为T
              WHERE T.COURSEID = C.COURSEID 
                          和C.DEPARTMENT ='计算机科学');

输出:

COURSEID 名称
CSE245 操作系统
CSE101 程序设计

说明:在课程关系中,计算机科学系中只有一个教师分配的课程是操作系统和编程。对应于这两个课程的唯一约束只有一个由相应教师组成的元组。因此,这两门课程的唯一条款评估为真,这些课程以输出关系显示。课程关系中的其他课程要么有两个或更多教师,要么不属于计算机科学系,因此,这些课程不会显示在输出关系中。

SQL | 独特的约束-IDC帮帮忙