2011-06-16 62 views
3

我知道我可以设置一个FK约束来确保Table1.ColA存在于 Table2.Key中,但是如果我想要做相反的事情呢?Postgresql 9.0中的反向FK约束?

我想确保Table1.ColA不存在Table2.Key ..我可以做 这与任何类型的CHECK约束,触发器,自定义函数等? 谢谢!

编辑:

比方说,我有一个名为 “名称” 表:

1 Michael 
2 David 
3 William 

现在我有一个表称为 “昵称”:

Mike -> 1 
Mikey -> 1 
Dave -> 2 
Bill -> 3 
Will -> 3 

我要确保没有人将“迈克尔”这一行添加到“昵称”中,因为它已经存在于“名称”中。

+0

请给我更大的图片吗?我怀疑还有其他方法可以做到这一点。例如,你想只在三个子表中的一个中允许一行吗? – gbn 2011-06-16 05:27:57

回答

2

标准SQL,您可以使用CREATE ASSERTION但PostgreSQL不支持它。您可以在两个表中触发器(例如UNION两个表,GROUP BY名称和测试COUNT(*) > 1或者可能只是测试逻辑inserted表值不出现在另一个表中)或其他程序代码。

您可以使用一个表格和一个明确的子类型来设计问题,并使用@gbn建议的常规UNIQUE约束。

+0

好极了,它听起来像一个触发器是我最好的选择然后..谢谢! – 2011-06-16 05:59:03

+1

没有主流的RDBMS支持CREATE ASSERTION当然... – gbn 2011-06-16 05:59:05

+0

啊,这些理论标准之一..就像HTML5一样。 – 2011-06-16 06:03:56

1

你有没有考虑使用一个表

  • “名称类型”(PRIMAR,昵称)
  • “的绰号” 这是一种自我FK

据我了解,你有一个应该是唯一的名称列表。

这将删除不需要任何代码保持“不FK”

+0

这肯定会起作用,但主表有一个非常复杂的模式,它自己的约束,索引以及读取它的几十个函数和视图。在那里放置额外的行,其中大部分为空的值只是指向同一个表中的另一行将是我不习惯的更改。 – 2011-06-16 05:52:05

+0

@Mike Christensen:写代码然后:你必须使用触发器。你可以分开名字(名字,名字类型),并将复杂的细节保存在PK(name,nametype)和PK的简单表格中,检查nametype = 1(对于主) – gbn 2011-06-16 06:01:00