我一直在学习数据库设计,我对1:1的关系感到困惑。根据我的理解,您只需将列添加到相应的表中即可。有人可以提供一个真实世界的例子,说明1:1关系是必要的,还是提供了一些重要的好处?即,我将在哪里使用1:1的关系,它会是什么样的?
答案 0 :(得分:6)
我会给你一个真实的例子。
在医疗账单领域,希望通过医疗保险获得报酬的医生通过为患者每次就诊创建听写报告来处理账单。这可能实际上是由秘书转录的录音音频听写,但更多时候它只是对他们所做的事情的书面描述以及与患者的谈话,以及历史,印象等等。然后,有执照的医疗编码人员会阅读此口述并决定允许医生开具账单。
与口述不同,有关于患者的人口统计信息:姓名,年龄,账单地址等。此信息必须严格地与有关口述的信息分开,以防止编码员允许倾向于掩盖他们的账单判断或侵犯患者的隐私。
这些数据通常在原点的数据系统中以1:多关系保持良好的标准化,并且在正确的时间只向正确的人显示正确的部分。但是,大量办事处将其计费功能外包给第三方。例如,这样一家小诊所就不必将持牌医疗编码人员留在工作人员身上;计费办公室的一名程序员可以满足许多诊所的需求。当数据从诊所发送到计费办公室时,患者的人口统计信息和听写需要作为单独的部分进行,可能在不同的时间。此时,它们可能会存储在完全独立的表中,并且具有1:1的关系和共享的ID字段,以便以后匹配它们。
在这种情况下,1:1关系与数据模型关系不大。您可能在导入时匹配记录,并且随着账单在系统中移动,最终在诊所的人口统计记录中收到的省级患者信息将与真人匹配,因此可以恢复1:多关系。否则,每次访问医生时,您都会在单独的帐户上单独声明。
相反,它几乎与系统设计有关。在我们想象的计费服务中,可能完全不同的人构建和使用计费部分与编码部分。通过这种方式,每一方都可以完全控制自己的领域,而且你确信没有人,甚至是开发者都没有违反任何隐私规则。
答案 1 :(得分:5)
真正的一对一关系很少 发生在现实世界中。这类 通常会创建关系以获得 围绕数据库的某些限制 管理软件而不是 模拟现实世界的情况。在 Microsoft Access,一对一 在a中可能需要关系 数据库必须拆分时 表格分成两个或多个表因为 安全性或性能问题或 因为255列的限制 每张桌子。例如,你可以保留 大多数患者信息 tblPatient,但特别注意 敏感信息(例如,患者) 姓名,社会安全号码和 地址)在tblConfidential(见 图3)。访问信息 在tblConfidential可能更多 限制比tblPatient。作为一个 第二个例子,也许你需要 转移只是一大部分 表格上的其他一些应用程序 定期。你可以拆分表 进入转移和 非转移件,并加入他们 以一对一的关系。
这是here: Fundamentals of Relational Database Design
的引用这是SO上的similar question。
我可以看到使用1:1(我过去使用它的地方)的另一个原因是,如果你有一个包含大量列的表,并且只有少数几个涉及非常密集和频繁的查询需要快速的,我会把它分成两个相关的表1:1我可以查询轻量级表并获得良好的性能,但仍然可以通过简单的连接轻松地与其相关的其他数据。
答案 2 :(得分:2)
我认为表格应该使用域背景设计。因此,如果这些列形成两个不同的实体,则不应将它们混合在一个表中。根据我的经验,1:1的关系往往随着时间的推移演变为1:n的关系。
例如,您可能希望存储某人的邮政地址。但过了一段时间后,您需要为每个人存储多个地址。将程序从1:1关系重构为1:n通常比从旧表中将一些列提取到新表中容易得多。
许多数据库系统允许以非常简单的方式定义每个表的访问权限。但是,在单个列上定义权限通常非常痛苦。
答案 3 :(得分:0)
如果X与Y具有1:1的关系,并且与Y具有1:1的关系,那么它是有用的.Y可以被抽象到共享表中,而不是在X和Z中重复。
编辑:一个真实的例子是客户,公司和地址。客户与公司之间可能存在N:N关系。但客户和公司都与地址有1:1的关系。某些地址行可能与客户和人员相关。
答案 4 :(得分:0)
首先,因为他们正在谈论Access(Jet,Ace,等等) - 感谢@Richard DesLonde发现这一点 - 然后他们可能正在谈论1:0..1的关系。我不相信真正的1:1关系在Access中是可行的,因为它没有延迟约束或在SQL PROCEDURE
中执行多个语句的机制。大多数Access从业者都满意使用1:0..1关系来建立真正的1:1关系,所以我想作者很满意使用术语“1:1”非正式地指代两者。
当然,1:1和1:1..0的关系在现实世界中很常见。我认为他们正在努力传达(有效)的观点,即出于商业目的,在数据模型中发明了一些1:1和1:1..0关系。
考虑“自然人”(即人)和“公司”。它们没有共同的属性(当然,两者都有“名称”但它们的域名不同,例如“自然人名”具有“姓氏”,“给定名称”和“标题”等的子原子域)。
但是,在给定的数据模型中,不同的实体类型可能扮演相同的角色。例如,“自然人”和“公司”都可以是“公司”的官员。在数据模型中,我们可以有两个不同的实体类型“自然人员”和“公司官员”,它们可能具有许多共同的属性,并且来自相同的域,例如预约日期,终止日期等;此外,他们的业务规则是相同的,例如预约日期必须在终止日期之前。而且,两者都将参与等效关系,例如“自然人代表”等。
数据模型可以在高级别“拆分”,从而产生非常相似的表对,例如“自然人员”和“公司官员”,“自然人员自然人代表”和“公司官员自然人代表”等。
然而,另一种方法是使用伪造的实体类型对公共属性和关系建模。例如,“自然人”和“公司”都可以被视为“法人”(除此之外:法律中存在“法人”这样的概念,但这意味着与现实中存在的相同世界?!)
因此,我们可以分别为“法人”和“自然人”和“公司”的子类别表提供超类表。 “官员”表将参考“法人”表。所有后续关系表都可以引用“人员”表,从这一点开始,这将是表的数量的一半。
这种“子类化”方法存在实际问题。因为“自然人”和“公司”没有共同的属性,所以它们没有共同的密钥,因此“法人”表需要有一个人工密钥,以及所需的所有问题,特别是如果它需要在应用程序中公开。此外,由于“法人”,“自然人”和“公司”之间的关系真正是1:1,一些DBMS,作为Access,将缺乏有效实施它们的必要功能,许多人将不得不满足于使它们1: 0..1。
答案 5 :(得分:-1)
1:1关系是您在数据中建模的抽象概念,但在数据库级别(假设RDBMS)并不存在。您总是在一个表上指向另一个表的外键,因此从技术上讲,FK指向的父表可能有多个子表。这是您希望在业务逻辑中强制执行的操作。
建模意义上的1:1关系的一个很好的例子是员工与人之间的关系。您有一个拥有某些数据的人,那么您在同一个人身上拥有额外的属性。在OO编程术语中考虑这一点的好方法是继承类。 Employee类继承自Person。事实上,ORM系统可能会在数据库中为每个具有共享主键的表建立1:1关系模型。