Oracle:更新时的选择性唯一性索引问题

时间:2011-07-20 00:27:29

标签: sql oracle indexing constants

我创建了选择性唯一索引

CREATE UNIQUE INDEX fn_unique_idx 
    ON table1 (CASE WHEN is_deleted='N' THEN id ELSE null END,
               CASE WHEN is_deleted='N' THEN name ELSE null END,
               CASE WHEN is_deleted='N' THEN type ELSE null END);

所以在任何时候我只想要一个带有is_deleted'N'的条目(id,name,type)。

插入工作正常,即当我尝试插入is_deleted ='N'时,它允许输入多个is_deleted'Y'并且产生唯一的constriant异常。

但是,当我尝试更新时,它正在飙升 oracle错误:

ORA-00600: internal error code, arguments: [qctVCO : bfc], [1], [0], [1], [871], [1], [2], [875], [], [], [], [] 


SQL : UPDATE table1 set is_deleted = 'Y' where id = 1, name = 'foo' and type =bar';

我想将此当前条目设置为已删除,并插入包含更新数据的新条目,并且is_deleted ='N'。这基本上是为了维护历史。

有人可以帮我解决这个问题。

感谢。

3 个答案:

答案 0 :(得分:1)

这种类型的错误是oracle内部错误 - 也就是一个bug ......

你在哪个补丁版本?也许就是以现在的情况为准。

答案 1 :(得分:1)

如果我理解您要完成的任务,您希望能够拥有多个具有相同(id, name, type)的行。对于其中一行is_deleted = 'N'以及其余行is_deleted = 'Y'

这是对的吗?

如果是这样,请允许我提出一些想法:

  1. 删除is_deleted字段。相反,有一个version字段,无论最新版本是什么,这都是未删除的行。然后,唯一约束/索引自然涵盖(id, name, type, version)。这可能会使查询变得复杂。
  2. 介绍3个新字段:archive_idarchive_namearchive_type。唯一约束仍涵盖原始(id, name, type)。通过将值移动到archive_*字段并将NULL(如果原始字段)移动来“删除”该行。这应该有效,因为包含所有NULL的元组不包含在(唯一)索引中。
  3. 有一个单独的档案数据表,没有唯一约束。
  4. 也许使用CONSTRAINT UNIQUE而不是UNIQUE INDEX?
  5. 另外,请告诉我们是否存在任何参照完整性限制?

答案 2 :(得分:0)

第3点上同意Branko。您还可以添加START& END可以在此单独的表中查看档案数据。