Oracle 空和唯一约束
Posted
技术标签:
【中文标题】Oracle 空和唯一约束【英文标题】:Oracle null and unique constraint 【发布时间】:2011-05-02 17:34:50 【问题描述】:唯一约束是否包含非空约束?
我有一个情况,一个属性cellPhone
可以是NULL
但不能重复,所以我给它两个约束:“not null”和“unique”,在更新记录的情况下,如果用户没有'不要输入我在字段中输入 0 的值,因此会出现此异常:
SEVERE: java.sql.SQLIntegrityConstraintViolationException: ORA-00001: unique constraint (TEST1.OSQS_PARENTS_CELLPHONE_UK) violated
UPDATE
的情况应该怎么办?
编辑 这是表ddl的定义
CREATE TABLE "TEST1"."OSQS_PARENTS"
( "PARENT_NO" NUMBER(38,0),
"PARENT_NAME" VARCHAR2(4000 BYTE),
"PARENT_ID" NUMBER(38,0),
"PARENT_EMAIL" VARCHAR2(30 BYTE),
"PARENT_CELLPHONE" NUMBER(38,0)
)
这是约束的图像
这是更新声明
Parent aParent; //is an object I pass through a function
String SQlUpdate = "UPDATE OSQS_PARENTS P SET P.PARENT_ID=?,P.PARENT_EMAIL=?,P.PARENT_CELLPHONE=?"
+ " where P.PARENT_NO=?";
PreparedStatement pstmt = null;
try
pstmt = con.prepareStatement(SQlUpdate);
pstmt.setLong(1, aParent.getId());
pstmt.setString(2, aParent.getEmail());
pstmt.setLong(3, aParent.getCellPhoneNo());
pstmt.setLong(4, parentNo);
pstmt.executeUpdate();
【问题讨论】:
这是否是一个合法的约束失败(即,您可能已经在受约束的列中有一条为 0 的记录)? 请显示完整的 CREATE TABLE 和约束定义以及相应的 UPDATE 语句。 @Simon,在用户没有输入手机值的第一次更新中,我将该字段更新为零,在第二次没有输入手机号码的用户中,我也尝试用零值更新记录,所以问题出在这里,我不知道我应该在更新语句中输入什么值。 正如@a_horse_with_no_name 所说 - 如果您发布包含约束和您正在使用的语句的表定义,我们将能够更好地提供帮助。但是,听起来您没有正确使用NOT NULL
- 如果该值可能是“未知”(您将替换为零),那么它真的应该是 NOT NULL
并且是唯一的吗?
@Alaa:不需要发截图。如果单击该窗口中的 SQL 选项卡,您应该会看到所有需要的 SQL。但更大的问题是,屏幕截图与您的错误消息不匹配。该错误指的是约束OSQS_PARENTS_UK4CELL_PHONE
,但从您发布的内容中看不到这一点
【参考方案1】:
听起来像这样:
cellPhone 必须是唯一的。当用户不输入值时,您将其标记为 0。因此,当您尝试将多个 0 值插入“UNIQUE”列时会失败。
我相信您需要删除列上的 NOT NULL 约束(允许它是唯一的,是的,但允许 NULLS)。
然后当用户没有输入值时,将其作为NO值(unknown = null 0 -- 0是已知值)
在你的语句中加入一个 IF,如果值那么你所拥有的,否则将它设置为 NULL!\
pstmt.setNull(3, java.sql.Types.INTEGER);
【讨论】:
+1。OSQS_PARENTS_NULLCHECK
约束确实有意义,假设每条记录都需要 PARENT_EMAIL
或 PARENT_CELLPHONE
,并将未知值设置为 NULL(允许它们在约束所涵盖的两个列中)是最好的方法
这背后的原因是Oracle实现了一个带有索引的UNIQUE约束,NULL值没有索引。这就是为什么你可以有多个不“冲突”的空值。
@Adam:NULL 没有索引,除非是多列索引,其中至少有一列不为空。以上是关于Oracle 空和唯一约束的主要内容,如果未能解决你的问题,请参考以下文章