如何正确索引与其他两个表具有一对多关系的表?

发布于 2024-08-23 13:23:10 字数 156 浏览 5 评论 0原文

想象一下我有三个表,分别称为“客户”、“公司”和“电话号码”。客户和公司都可以拥有多个电话号码。索引phone_numbers 的最佳方法是什么?同时拥有 customer_id 和 company_id 并将其中之一保留为空?如果有两个以上的表与phone_numbers 具有一对多关系怎么办?

Imagine I have three tables, called "customers", "companies" and "phone_numbers". Both customers and companies can have multiple phone numbers. What would be the best way to index phone_numbers? Have both customer_id and company_id and keep one of them null? What if there are more than two tables with a one-to-many relationship with phone_numbers?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

自由范儿 2024-08-30 13:23:10

您的业​​务规则可能只规定一对多,但实际上人和人之间的关系。公司之间可以是多对多的关系。一个人可以有很多电话号码(家庭电话、手机号码等),而一个电话号码可以与很多人(我自己、我的另一半等)相关。同样,公司号码和我的公司号码可以相同 - 您只需使用分机号码即可直接联系我。

对外键建立索引是一个好主意,但要注意过早的优化。根据设置,我会考虑对电话号码列进行唯一约束,但我不会将电话号码列本身作为主键。

Your business rules might only state one-to-many, but in reality people & companies can be a many-to-many relationship. One person can have many phone numbers (home, cell, etc), and a phone number can relate to many people (myself, my significant other, etc). Likewise, a company number and my business number can be the same - you just use an extension number to reach me directly.

Indexing the foreign keys would be a good idea, but beware of premature optimization. Depending on setup, I'd consider a unique constraint on the phone number column but I would not have the phone number column itself as a primary key.

无尽的现实 2024-08-30 13:23:10

我会在客户和公司表中使用身份列,然后在电话号码表中按照您所说的操作,将一个保留为空,另一个填充。我做了类似的事情,只要您验证数据,这样它就不会在两个值都为空的情况下运行,效果很好。对于更优雅的解决方案,您可以有两列:一列是 id,另一列是类型标识符。假设 1 代表客户,2 代表公司,这样您就不必担心空数据或大量额外列。

I would go with identity columns in the customer and company tables, then in the phone number table do as you said and keep one null and the other populated. I do something similar to this and it works out fine as long as you validate data so that it doesn't go in with both values being null. For a more elegant solution you could have two columns: one that is an id, and another that is a type identifier. Say 1 for customers and 2 for companies, that way you don't have to worry about null data or a lot of extra columns.

水波映月 2024-08-30 13:23:10

我将向phone_numbers 表添加两列。第一个是一个索引,告诉您要与哪个表关联(例如,1 = 客户,2 = 公司)。第二个是相应表的外键。

这样您就可以添加任意数量的电话号码源。

如果某一个人或公司有多个电话号码,则phone_numbers 表中将有多行。

I'd add two columns to the phone_numbers table. The first would be an index that tells you what table to associate with (say, 1 = customers and 2 = companies). The second would be the foreign key to the appropriate table.

This way you can add as many phone number sources as you want.

If a particular person or company has more than one phone number, there would be multiple rows in the phone_numbers table.

瀟灑尐姊 2024-08-30 13:23:10

我最接近模式的东西如下——任何两个具有多对多关系的实体都需要它们之间有一个关联实体(交叉引用表),就像这样(假定代理键):

CREATE TABLE CUSTOMER_XREF_PHONE
( CUSTOMER_ID      NUMBER NOT NULL,
  PHONE_NUMBER_ID  NUMBER NOT NULL,
  CONSTRAINT       CUSTOMER_XREF_PHONE_PK 
    PRIMARY KEY      (CUSTOMER_ID, PHONE_NUMBER_ID),
  CONSTRAINT       CUSTOMER_XREF_PHONE_UK 
    UNIQUE           (PHONE_NUMBER_ID, CUSTOMER_ID),
  CONSTRAINT       CUSTOMER_XREF_PHONE_FK01
    FOREIGN KEY      (CUSTOMER_ID)
      REFERENCES       CUSTOMER (CUSTOMER_ID) ON DELETE CASCADE,
  CONSTRAINT       CUSTOMER_XREF_PHONE_FK02
    FOREIGN_KEY      (PHONE_NUMBER_ID)
      REFERENCES       PHONE_NUMBERS (PHONE_NUMBER_ID) ON DELETE CASCADE
);

这样的实现模式可以:

  • 受到数据库级引用完整性约束的完全保护

  • 支持双向访问(有时您需要查看还有谁拥有该电话号码)

  • 清理

  • 通过使用“关系类型”属性来映射实体之间的多个独立关系来进行扩展,
    如:

    • 客户有家庭电话号码
    • 客户有白天电话号码
    • 客户有传真电话号码
    • 客户有手机号码

The closest thing I have to a pattern is the following -- any two entities with a many-to-many relationship require an associative entity (a cross-reference table) between them, like so (surrogate keys assumed):

CREATE TABLE CUSTOMER_XREF_PHONE
( CUSTOMER_ID      NUMBER NOT NULL,
  PHONE_NUMBER_ID  NUMBER NOT NULL,
  CONSTRAINT       CUSTOMER_XREF_PHONE_PK 
    PRIMARY KEY      (CUSTOMER_ID, PHONE_NUMBER_ID),
  CONSTRAINT       CUSTOMER_XREF_PHONE_UK 
    UNIQUE           (PHONE_NUMBER_ID, CUSTOMER_ID),
  CONSTRAINT       CUSTOMER_XREF_PHONE_FK01
    FOREIGN KEY      (CUSTOMER_ID)
      REFERENCES       CUSTOMER (CUSTOMER_ID) ON DELETE CASCADE,
  CONSTRAINT       CUSTOMER_XREF_PHONE_FK02
    FOREIGN_KEY      (PHONE_NUMBER_ID)
      REFERENCES       PHONE_NUMBERS (PHONE_NUMBER_ID) ON DELETE CASCADE
);

Such an implementation pattern can:

  • Be fully protected by database-level referential integrity constraints

  • Support bi-directional access (sometimes you need to see who else has that phone number)

  • Be self-cleaning if your database supports ON DELETE CASCADE

  • Be extended through the use of a "relationship type" attribute to map multiple independent relationships between the entities,
    such as:

    • customer has a home telephone number
    • customer has a daytime telephone number
    • customer has a fax telephone number
    • customer has a mobile telephone number
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文