Database design 数据库设计,包括人员和组织

Database design 数据库设计,包括人员和组织,database-design,relational-database,subtyping,Database Design,Relational Database,Subtyping,我最近在关系数据库设计中发现了子类型/超类型方法,因此我提出了一个问题:这是一个正确的设计,混合了子类型/超类型设计方法吗 在此之前,我将人员和组织作为两种不同的类型进行了讨论。我明白,让聚会成为人和组织的超级类型是一种更好的方法。现在,解决了这个问题后,添加地址和附加地址既适用于组织,也适用于人员,从而将他们连接到超类型的方 此外,我需要记录的不同人群,如员工、项目联系人和供应商联系人。这些人都是一方中不同类型的人。这是将表与人员连接以实现此目标的正确方法吗?链接到组织表的供应商和债务人也是如

我最近在关系数据库设计中发现了子类型/超类型方法,因此我提出了一个问题:这是一个正确的设计,混合了子类型/超类型设计方法吗

在此之前,我将
人员
组织
作为两种不同的类型进行了讨论。我明白,让
聚会
成为
组织
的超级类型是一种更好的方法。现在,解决了这个问题后,添加
地址和
附加地址既适用于
组织
,也适用于
人员
,从而将他们连接到超类型的

此外,我需要记录的不同人群,如
员工
项目联系人
供应商联系人
。这些人都是
一方中不同类型的
。这是将表与
人员
连接以实现此目标的正确方法吗?链接到
组织
表的
供应商
债务人
也是如此,因为
供应商
债务人
始终是
组织

我相信这是一种很好的设计方法,但我可能会错过一些主键和外键,尤其是在查看
供应商联系人时。有一个外键
partyid
,它应该指的是
person
,还有一个外键
supplierid
,但是这个
supplierid
也指的是它自己表中的某个
partyid
。能够从这个表中查询信息,这不是一件非常困难的工作吗?这种设计是否合适

我主要担心的是,许多表需要引用一个人或一个组织,而不是到处都有两个外键,始终保留一个空值,因为我存储了一个人或一个组织的记录,现在我只有一个外键:
partyid


我不太清楚你在这里问的问题

我不知道有任何数据库引擎在本地支持子类型-它们用于概念建模,在物理设计中,它们是用数据库引擎支持的任何东西实现的

将其建模为物理数据模型可能更有用,因为关于主键和外键的决定几乎肯定会根据物理表示子类型的方式而改变

有几种方法可以将“子类型”的逻辑概念转换为物理数据模型-最常见的三种方法是:

  • 每个子类型的表。这意味着您的外键可能需要链接到多个表(例如“person”或“organization”),但您的查询/连接非常简单
  • 具有公共属性的超类型表,子类型数据的单独表(例如“party”、“person”和“Organization”)—在这种情况下,外键指向“party”,但要获取子类型数据,必须包含子类型表的联接。这会使SQL变得复杂
  • 具有许多可为空列的公共表(例如“party”,所有列均表示个人和组织)。这使得外键变得简单——但同样,您的数据访问逻辑变得混乱
为了帮助您评估设计,有必要通过SQL查询解决一些明显的问题,例如“供应商x的主要联系人的电话号码是多少?”、“有多少人在项目y上工作?”以及您的模式如何支持这些问题

答案取决于答案。

您使用了
parties
表(开发人员的常见陷阱之一)的主键,同时无法检测到
parties
表中的行实际上是未加入人员或组织表的人员或组织
因此,当您在其他表中将
各方的PK
用作FK时,如果该方是所需的一方,则无法检测到该PK,您正在失去业务逻辑,这是使用代理密钥的副作用。

解决方案:为parties表选择一个自然键。
建议在parties表中有一个名为
party_type
的鉴别器列(枚举值为person=1和organization=2)
parties表的主键可以是
{party\u name+party\u type}

在聚合表中,如
SupplierContacts
,对
{party_type=1
}具有检查约束将解决问题。


请注意,该解决方案旨在解决数据库设计级别的问题,作为替代方案,您可以在应用程序级别进行额外的工作,以归档数据完整性(建议较少,但主要由开发人员使用!)

感谢您的快速响应。此模型可能有点不清楚,设计速度可能较快,这就是为什么有些表不同于我打算为表名编写的复数形式。这是实际结构的一小部分,即员工存储了更多信息,如首字母和函数。供应商还存储了有关其是否为维修和维护供应商或下订单供应商的信息。我的任务主要涉及逻辑设计,因为我以前从未使用过超级/子类型,我想知道这是否是表示我要单独存储的信息的正确方法。每个子类型的表是我试图避免的,所以选择具有公共属性的超类型表。复杂的查询确实是我担心的问题,但这似乎是一个更符合逻辑的设计。谢谢你的回答,我现在就结束这个问题。你所说的“如果对方是你想要的那一方,那么你就无法察觉”是什么意思?我通常不想单独引用party表,如果这是您的意思的话(我现在知道partyname是一个