2010-03-26 61 views
14

使用一对一表关系而不是简单地将所有数据存储在一个表中的优点是什么?我理解并使用一对多,多对一和多对多的方式,但实现一对一关系似乎是一项单调乏味且不必要的任务,特别是如果您使用命名关联(php)对象到数据库表的约定。使用一对一表关系的优点是什么? (MySQL)

我无法在网络或本网站上找到任何可以提供一对一关系的真实世界示例。起初我认为将用户分成两个表格是合乎逻辑的,例如,将两个表格分开,其中一个包含像关于我的个人资料页面的公共信息,另一个包含诸如登录/密码等私人信息。但是为什么要去通过使用不必要的JOINS的所有麻烦,只要选择哪个字段可以从该表中选择呢?如果我显示用户的个人资料页面,显然我只会选择ID,用户名,电子邮件,aboutme等,而不是包含他们的私人信息的字段。

任何人都在意用一些一对一关系的实际例子来启发我吗?

回答

6

我已经使用一对一的关系来扩展现有应用程序中的某些功能,而不会影响应用程序数据库结构。这是扩展现有数据库表的一种不显眼的方式。

使用一对一关系的另一个原因是实现类表继承,其中层次结构中的每个类都有一个表,并且一个对象在其父类中的表类中具有对应的行表,在他的祖父母课堂表等等。

见,例如,学说2 Class Table Inheritance Page

+1

-1表示在关系数据库中使用装饰器模式是一个好主意。 – symcbean 2010-03-26 12:21:16

+5

是的,我的意思是在byronh给出的意义上延伸。但是,我没有说这是一个好主意,我只是说它可能是一个原因。如果一件事情是好的,它也取决于上下文。有时我不想要,我也不能更改第三方数据库,所以我用一对一的关系“扩展”那个表 – 2010-03-26 22:08:47

+0

是的,还要注意ALTER TABLE在大数据行(数千行)表中添加一列,可能需要很多时间(小时)。与此同时,桌子被锁定,系统管理员可能在夜间醒来...... – Qlimax 2015-07-21 12:42:13

9

一种可能的用途是部分信息是可选的。这样,您不需要在一个大表中包含一堆可空的字段,但可以将其逻辑分隔为强制表和可选表。

其他用途是当某些数据与不同的表共享时。例如,假设您有一个销售电脑零件的网站。你可以把所有组件共享的细节放到例如。 “零件”表,但将具体细节放在“主板”,“cpus”等中,这些只是使用具有一对一关系的零件表。

1

即使只有一部分字段正在被读取,数据库引擎可能不得不将整行加载到内存中以便从中获取数据。每行更少的字段意味着每页更多的行,这意味着更少的磁盘访问。

+0

如果您使用正确的数据库引擎,并且明智地编写了sql和索引,则不应该如此。 – Whakkee 2010-03-26 08:11:25

+0

如果您使用MySQL(MyISAM/InnoDB),则除了仅用于键的SELECT之外,其他任何性能都会受到影响。表空间越大,获取请求的数据所需的内存就越多。同时更新性能会受到重创。 – Jacco 2010-03-26 11:41:52

6

这里的二,我相信其他人会发布更多

  • 要在不实际修改表扩展现有的表。也许它是由第三方供应商提供的,并且您希望通过简单地拥有共享相同密钥的第二个表来分隔您的扩展。
  • 也许在表中有固定宽度的列经常被访问,而可变的列则不是。在这种情况下,对于频繁的东西,有一个固定行长的表可能会提高效率,其他所有的次表都会有效率提高。

此外,规范数据库时,说3rd Normal Form (3NF)你可能会发现你有哪些是不是真的“约”的关键,需要拉出一个单独的表列。

0

当我们需要用too many fields(96场!)扩展我们的一个表时,我们使用了“一对一关系”。所以,我们创建了另一个表格并将每个新的字段放在里面。

无论如何,这种方法我喜欢的是:

Table_Base: 
    ID 
    MANDATORY_FIELD 
Table_Option: 
    ID 
    OPTIONAL_FIELD 
5

专门为您例如: 你不希望像存储在同一个表作为登录名和密码信息的姓名和地址的用户信息,因为这您可以授予组织中的某人对用户信息表的权限,而不是登录数据表中的权限。我不同意其他人关于“一桌一桌”的主题。如果有许多字段,并且在表单或报表中不需要它们,则可以使用sql选择所需的字段,甚至可以使用视图来确保不会获得太多的数据。

+0

您也可以授予对特定列而不是整个表的访问权限。但是表格(不仅仅是单元格)会带来性能问题。如果不选择所有字段,表空间仍然必须加载到内存中;这与意见没有什么不同。这条规则的唯一例外是如果可以直接从键索引中检索请求的数据。 – Jacco 2010-03-26 13:59:23

1

在OO中你有继承。因此,您可以拥有一个包含父对象数据的表格,以及其他包含特定于子项的字段的表格。

4

最常见的原因是,这种关系可以是非强制性的。即存在适用于每个基本实体的一组属性,但是仅适用于子集的一些属性。

这样做的另一个有效原因是控制访问权限 - 您可能会在整个应用程序中使用一张客户表,尽管每个客户都有密码和信用卡,但您可能希望限制可见性/更新权限。

Marga Keuvelaar对Ignacio Vazquez-Abrams的评论回答是错误的。您可以使用更好的DML/DDL缓解影响,但不是在所有情况下。但是,您需要对数据模型的透明度与性能优势进行权衡 - 这需要经过仔细考虑。

C.

+0

此答案中引用的评论现在已消失。 – Cypher 2014-04-08 00:22:31

0

除了已经取得的说,

一些列可能会比其他人不同的“安全审查”的要求。例如。一名雇员的名字可能比他的薪水“更公开一些”。现在,数据库管理系统通常不强制使用列级别的安全性,但通常会使用表级别的安全性。

因此,通过在单独的表格中挑出工资,您只需使用DBMS的安全设施即可为自己购买实现用户安全需求的可能性。根据我的经验

0

一件事还没有被提及:

分成两个表也有助于创建模型类。假设你有Customers表和DriverLicense表和它们之间的一对一关系。如果您使用实体框架,我敢打赌,如果您有两个单独的表格,应该会更好,因为您的应用程序中可能有两个模型类,即Customer类和DriverLicense。通过这种方式,实体框架可以很容易地将一个新的驱动程序许可证信息稍后添加到现有客户,或删除和更新它。简而言之,考虑到Web开发方面,我认为如果它们是两个不同的实体,即使它们具有一对一的关系,它们也应该有自己的表。