没有主键与复合主键

时间:2016-03-10 01:39:37

标签: sql database-design

我的方案是有一个用于记录和报告用户可以在我们维护的一组站点中更改的重要设置的表(每个站点都有自己的数据库)。当我设计表格(将在每个数据库上部署)时,如果我需要Primary Key,我会感到困惑。我有一个名为SiteID的列,日志记录表中的每一行都有SiteIdnewVal of SettingoldVal of settingChange date。我将使用它来查看网站上的更改历史记录,按日期过滤更改等。因此,在这种情况下,显然SiteId单独不能是PK,但是我真的必须添加一个像LogId这样的新列可以制作复合P K?我在这里错过任何东西吗?

4 个答案:

答案 0 :(得分:1)

没有重复行的表始终具有至少一个候选键。我们可以选择一个来通过PRIMARY KEY申报;任何其他人都是UNIQUE NOT NULL。 (UNIQUE NOT NULL是您从PRIMARY KEY声明获得的约束。)如果您没有告诉 DBMS您的候选键,那么它就不能例如,通过在列上隐式定义索引来防止重复或提高性能,从而帮助您减少错误。

从你的问题中不清楚你如何记录给出新的& amp;旧的价值观是为了。如果您的列为siteIdsettingnewValueoldValue& changeDate然后您的表格中有一个候选键(siteID, setting, changeDate)。作为唯一的候选键,它是主键。如果设置值标识了设置,那么您的列就是siteIdnewValueoldValue& changeDate然后您有两个候选键(siteID, newValue, changeDate)(siteID, oldValue, changeDate)。每个都应该得到UNIQUE NOT NULL约束。一个可以通过PRIMARY KEY声明。

如果添加另一列unique / surrogate / id值,则该表具有另一个候选键。如前所述,通过UNIQUE NOT NULL约束来约束所有约束,其中一个约束可以通过PRIMARY KEY来表达。有理由添加这样一个唯一/代理/ id列,但不是因为没有主键,除非该表会有重复的行。

答案 1 :(得分:1)

你需要专注于你的用例,主键很好,就像提到她一样。

如果您确定可以避免数据重复(例如:从应用程序端)并且您知道您的数据,并且知道您需要什么类型的索引等,您可以轻松避免这种情况,主要是因为您正在讨论用于报告的大量扫描当数据重复不成问题时。

在许多MPP数据库(以报告为目标的数据库,例如:vertica)中,主键是可选的。 所以,如果你知道你的数据和用例,你可以避免的主键是

谢谢。

答案 2 :(得分:1)

所有实体表都应该有PK,而不是所有表。历史记录/日志表通常没有PK,因为它们代表事件,而不是实体。 (相反,他们不需要PK。我已经看到他们定义了一个(通常是自动生成的)但我还没有看到查询中使用的值。就我而言能说出来,它们完全是多余的。)

所拥有的历史记录和日志表是时间戳字段和表示发生了什么事件的字段。记录的其余部分将包含某种实体信息,包括实体PK,以及与事件有关的其他数据 - 例如指定OP之前和之后的值。

时间戳列将与实体ID一起编制索引(因此可以检查在一段时间内在指定实体上发生的所有事件)和/或事件ID(因此可以检查所有实体)指定的事件发生在一段时间内)。这一切都取决于表中所需的信息类型。

答案 3 :(得分:0)

我会像这样制作架构

  

{ SiteId,版本,设置,更改日期}

因为,你可以在以前的版本中找到旧的设置,所以保持每个版本的值都没问题。

当然,您也可以使用更改日期为PK,如下所示:

  

{ SiteId,更改日期,设置,}

如果日期是包含时间且您的方案允许,则使用日期和网站ID更好。