SQL: реляционный дизайн БД - несколько FK для одной таблицы - PullRequest
1 голос
/ 30 марта 2011

Я надеялся, что кто-нибудь скажет мне, будет ли это плохой дизайн базы данных:

Допустим, у меня есть две таблицы:

Person  
Contract

И, скажем, я получаю два типа контрактов,единый договор (в котором участвует только один человек) и совместный договор (в котором участвуют два человека).Других перестановок нет.

Было бы проще всего настроить таблицу контрактов с двумя полями FK, одно из которых может иметь значение NULL, то есть:

Контракт:

ContractID     Description               PersonID      PersonID_Second
1              Single person contract    1112          NULL
2              Joint contract            1073          900

Это плохая идея?

Спасибо
Карл

Ответы [ 3 ]

4 голосов
/ 30 марта 2011

"Это плохая идея?"- Вообще-то да.Потому что, что происходит, когда вам нужно 3, 4 человека в контракте?

Вместо этого создайте таблицу соединения "многие ко многим" между контрактом и персоной, ContractPerson, содержащую ContractId, PersonId

2 голосов
/ 30 марта 2011

Еще два цента: эквивалентны ли отношения между двумя лицами и Контрактом? Есть ли «первый» и «второй за поездку» человек, или они оба имеют одинаковую важность в отношении этого контракта? И является ли различие между контрактами с одним и двумя лицами (и, возможно, будущим N-лицом) контрактами важным атрибутом контракта?

  • Если отношения эквивалентны, используйте решение Митча "многие ко многим".
  • Если есть важное различие между первым и вторым, исправление множественных FK [Parched Squid [говорит, что это сделало мое утро лучше!] Будет хорошо работать.
  • Но если вы предвидите контракты с N-лицами, придерживайтесь принципа «многие ко многим» с дополнительным атрибутом в таблице отношений, указывающим, «какие» отношения назначаются.
  • И если вам нужно отсортировать свои контракты, чтобы найти или отсортировать по 1, 2 или N-человекам, было бы удобнее иметь дополнительный атрибут, указывающий тип контракта, а не реализовывать множество объединений и логика нулевой проверки для подсчета связанных лиц каждого контракта.
2 голосов
/ 30 марта 2011

Я согласен с Митчем в том, что при всех равных условиях описанный вами случай лучше подходит для отношения M: N.

Однако, на общий вопрос о том, «несколько FK в одной таблице»по своей сути плохо: я так не думаю.Например, если у Person и SecondPerson были принципиально разные цели, вы бы назвали поля после цели, а не таблицы, на которую они указывают.Поэтому вместо PersonID, PersonID_Second, вы бы назвали их SalesDudeID и ManagerID.

В этом случае было бы менее идеальным использовать таблицу M: N, поскольку было бы менее понятно, какой из них является SalesDudeID икоторый был ManagerID.Кроме того, вопрос «что произойдет, если есть 3 или 4» можно перевернуть, чтобы не предполагать, что схема не расширяема, но что схема M: N допускает недопустимые данные (если 3 и 4, как вы говорите, недопустимы).

Опять же ... Я согласен с Митчем на конкретный вопрос.Я просто прочитал вопрос, как будто Карл упростил сценарий использования для ясности и хотел поговорить с более общим вопросом, который он мог или не мог иметь в виду.+1 к Митчу.

...