2011-05-23 69 views
4

我碰到,我似乎无法来解决的问题。主键应该是什么?

例如说,我与即将到来的视频游戏发布的表:

GAME 
game_ID | title    
----------------------------- 
1  | Super Mario 
2  | Final Fantasy XIII 

然后我有一个表releasedates(不同日期PS3和XBOX360只是为参数的缘故):

RELEASES 
game_ID | releasedate | platform 
--------------------------------- 
1  | 20-04-2010 | Wii 
2  | 23-03-2010 | PS3 
3  | 20-03-2010 | Xbox360 

现在,我已经把game_ID作为主键在表格“GAME”中。而game_ID也是表“RELEASES”中的外键。作为后者的主键,我应该有什么?似乎没有必要在“RELEASES”表中创建另一个ID键--table?

我可以以某种方式使用game_ID和平台共同打造的主键?如果是这样,SQL将如何?

回答

9

就像你创建一个仅包含一列的主键,您可以创建一个包含game_idplatform复合键:

PRIMARY KEY(game_id, platform) 
+0

作为这么简单,是吧? =) 是否有使用复合键的任何缺点? – Marcus 2011-05-23 13:04:27

+0

没有技术缺点。我能想到的唯一缺点是在Steve Mallory和Paul Alan Taylor的回答中提到,但在我看来,这是根据具体情况决定的...... – 2011-05-23 13:17:13

4

你不想game_ID作为主键和外键在发布表中。这会阻止表格为每个游戏创建多个记录,因为主键必须是唯一的。我会推荐一个这样的结构。

RELEASES 
release_ID | game_ID  | releasedate | platform 
--------------------------------------------- 
    1   |  1  | 20-04-2010 | Wii 
    2   |  1  | 23-03-2010 | PS3 
    3   |  1  | 20-03-2010 | Xbox360 

release_ID将自动生成。您可以通过在主键中包含平台来使用复合键,但如果单个游戏/平台具有多个版本,则可能会遇到问题。你现在可能不认为这是可能的,但事情会改变。

我也认为从不使用具有任何意思作为关键的列的良好做法,因为事情会发生变化,您无法预测它们将如何变化。如果你的密钥对最终用户没有意义,那么他们不能混淆你数据库的结构。

+0

它有一个带有game_id和platform的组合键,所以每个游戏都可以在多个平台上进行多次启动。然而,我投票赞成,因为我同意添加release_id作为PK – 2011-05-23 13:13:51

+0

@Tudor我在主键(game_id,platform)上的问题是在** same **平台上的多个版本,虽然现在可能不是问题,可能会在未来。 – 2011-05-23 13:20:19

+0

该案例可以通过向组合键添加发布日期来解决 - 但这并不好, – 2011-05-23 13:22:23

3

首先,考虑实现平台作为一个单独的查找表。这不仅可以减少数据损坏的可能性,还可以使您的密钥定义更加简单。

主键不必被限制为一个字段。您可以使用多个字段定义复合主键。

但是,在这种情况下,我建议不要使用复合主键,并且会主张在Releases表上创建一个新的主键。

为什么?那么,对于初学者来说,我认为你没有在发布中获得足够的信息。例如,视频游戏通常在不同地区的不同时间发布,因此在同一游戏和平台上发布两个版本可能是完全有效的。在这种情况下,您需要一个由三个字段组成的复合主键。它在哪里结束? :)

通过将ReleaseID定义为代理主键,您将给自己更多的空间进行更改。