如何在主键上创建SQL约束以确保它只能被引用一次?

时间:2017-07-14 15:22:50

标签: sql postgresql

如何添加约束以防止主键只能被引用一次?(可以在两个表中引用) 每个引用都应该具有主键之外的唯一值。

Table A
----------------------
id            
1             
2
3
4             

Table B
----------------------
id            a_id (foreign key to table A.id)
1             2
2             3


Table C
----------------------
id            a_id (foreign key to table A.id)
1             1

我希望在尝试将a_id = 2插入到表C中时,会发生错误,因为它已经在表B中使用了。

4 个答案:

答案 0 :(得分:2)

您可以在每个子表上使用INSERT,UPDATE触发器,以确保即将插入或更新的父表的PK在其他子表中不存在。

答案 1 :(得分:1)

您要执行的操作需要另一个表D,这有助于统一对A的引用。 表格D将包含自己的主键(Id),对表A的引用,其上有UNIQUE约束(称之为AId),以及第三列(称为"RowType"),用于指示行对应于哪个子表(BC)。您可以将此列设置为int类型,并为"0"分配值B,为"1"分配C

然后在表B中,您将一个外键添加到D.Id,将另一列"BRowType"添加为D.RowType的外键;然后你在这个列上定义一个约束,所以它只能有值'0'(或者你决定对应于这个表的任何值)。 对于表格C,您的约束会将值限制为'1'

当然,为了将记录插入BC,您首先需要在D中创建记录。但是,如果B中的记录引用了D中的记录,而该记录又链接到A中的记录,则您将无法再在{{{}}中创建记录1}}用于C中的同一行 - 因为A上的UNIQUE约束和D.AId上的约束。

答案 2 :(得分:0)

如果我正确理解了这个问题,听起来你需要在每个引用主键的表的列上添加一个唯一约束。

例如:

Table A
----------------------
id (primary key)
1
2
3

Table B
----------------------
id            a_id (foreign key to table A.id)
1             2
2             3

将a_id列设置为UNIQUE,这样可以确保表A中的主键不会被使用两次。您可以在每个引用A.id

的表中执行此操作

答案 3 :(得分:0)

如果您想避免使用触发器,可以创建一个带有id和唯一约束的表X. 在将记录插入B或C的每个事务中,您也必须插入X.只有在另一个表中没有插入时才能进行插入。