2009-11-04 118 views
2

我有2个数据库表:团队和游戏。应该将多对多的数据关系视为多对多关系吗?

对于这个问题,我们正在处理足球(足球)队和比赛。

每场比赛都有两支球队,一般是主队和客队,尽管偶尔两队都可以保持中立。

我的问题是我是否应该在Games表中使用2个外键(home_team_id,away_team_id)来表示这种数据关系,还是我应该使用与games_teams表的多对多关系来链接这两个表,其中我还需要存储球队是主队还是客队,看起来有点矫枉过正。

为了增加混淆,我使用KohanaPHP中的ORM库,并且这些将期望fk被称为team_id或链接表只包含2列。如果你在KohanaPHP有这个问题的经验,那么请留下回复,否则任何一般建议也非常感谢。

+0

如果你不打算远远这个(游戏在中立的地方等),保持简单,我会说。 我曾经做过类似的事情,只是在游戏桌上有两个外键。 然而,我不能帮你的是KohanaPHP的东西,这就是为什么我不会发布这个答案;) – Franz 2009-11-04 16:05:36

+1

感谢您的想法家伙,似乎每个人都同意使用2 fk的。指向Malphas,因为他是第一个回答,并没有很多(像我):) – Matt 2009-11-04 16:18:25

+2

只要确保评论WTF你这样做下一个程序员不会出现,不知道这种关系如何工作 – 2009-11-04 16:22:11

回答

3

如果您希望能够在您的数据库服务器上固定“Xth Normal Form”徽章,那么它应该被视为多对多,否则,我认为您会减少查询开销您只需要通过加入1个表,您希望获得一些有用的数据。

+0

我不同意。两张桌子的设计至少是BCNF,在这种情况下进一步无用。 – 2009-11-04 16:08:31

+0

意志提前12秒,也正确。解除归一化可以成为你的朋友。 – 2009-11-04 16:09:10

8

只要使用两列,否则你只需要在joiner表中限定它。这不像是一个睡觉的定时炸弹,突然有一天,你会发现你需要有一个真正的多到很多。

+1

+1睡眠定时炸弹 – 2009-11-04 16:07:07

+0

也许这些规则会改变,以便6个团队玩六角... – 2009-11-04 16:07:14

+4

虽然严重。威尔是对的。速度更快,而且特定的要求不会很快改变。 – 2009-11-04 16:08:03

5

2列在我看来是完全适合的。任何游戏只能有两个团队的事实通过具有两列来反映在数据库模式中。通过引入链接表,您可以引入单个游戏可能包含2个主队和2个客队的可能性,并且您需要额外的验证以确保此场景从不发生。通过将事物分离到两列,您的模式固有地强制数据完整性。

+0

这是不正确的。如果您指定两列是唯一的。 – 2009-11-04 16:15:00

+0

对不起,我可能有点不清楚。我所说的是,链接表方法允许2个主队(或者任何数目)的可能性,因此需要对其进行验证。你说得对,列可以通过两列方法变得独一无二。 – 2009-11-04 16:24:19

2

就规范化而言:是的。只有一对多或多对多可以分解为一个或多个一对多关系。

但现实地说,如果我要保存像GENDER这样的东西。我真的需要一个多国和​​一个日期时间戳附加到此?

令人惊讶的答案是肯定的 - 但只有当我出于商业原因需要跟踪性别变化时 - 对于大多数实际目的,答案是否定的。

我会保留一个表与两个键 - 除非有商业原因跟踪它。

1

根据你如何抽象它,我会说足球比赛必须有两支球队,在这种情况下,在比赛表中有列不仅更方便,更正确。

我甚至可以想象团队ID是游戏主键的自然部分。

1

完全认为你不应该有一个单独的表。程序员更容易,数据库更容易。很好想想如果,但听起来你已经有了。不要被认为正常化总是为所有事情走的路。

1

我尊重对方的回答,说使用两列是最佳选择,但是,您提到您在Kohana中使用ORM库。通过在游戏桌中使用两列,您将失去ORM功能以实现多对多关系。如果你设置了一个games_teams透视表,你可以做到以下几点:

$game = ORM::factory('game', 1); // 1 is the game id 

然后你可以遍历在那场比赛的球队:

foreach ($game->teams as $team) { 
// do stuff with $team 
}