【问题标题】:Which alternative to choose for a database redesign (sports stats, competitions, geographic scopes)? [closed]为数据库重新设计(体育统计、比赛、地理范围)选择哪种替代方案? [关闭]
【发布时间】:2011-05-16 17:16:44
【问题描述】:

我正在扩展一个关于运动统计数据的数据库。不同的联赛,或者更准确地说是“比赛”,可以用类似于某些地理区域(参与球队的范围/范围)的树状结构来表示:

1.洲际赛(大陆) ↑ 2.国赛(国) ↑ 3. 区域赛(地区) ↑ 4.州赛(州) ↑ 5.区赛(区)

(箭头表示父地理区域实体(树结构)的 FK。)

这里是视觉设计:


(来源:kawoolutions.com

我创建了一个“地理区域”层次结构,基本上只是为了实现范围竞赛层次结构。每个竞争实体都有一个地理区域的参考,例如每个州都知道它的(子国家)地区(parent_id)。

每个地理区域-比赛组合封装了三条信息:比赛类型(联赛、杯赛、季后赛……)、地理区域类型(参赛球队的范围!)和地理区域名称。

以下是我想插入数据库的比赛:

INSERT INTO Competitions (geo_area_id, type, label) VALUES ( 88, 'league', 'Deutsche Meisterschaft');         -- 'Country Championships Germany'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (248, 'league', 'Regionalmeisterschaft Nord');     -- 'Region Championships North'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (249, 'league', 'Regionalmeisterschaft West');     -- 'Region Championships West'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (250, 'league', 'Regionalmeisterschaft Sued');     -- 'Region Championships South'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (251, 'league', 'Regionalmeisterschaft Ost');      -- 'Region Championships East'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (258, 'league', 'Landesmeisterschaft Hessen');     -- 'State Championships Hesse'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (268, 'league', 'Bezirksmeisterschaft Darmstadt'); -- 'District Championships Darmstadt'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (269, 'league', 'Bezirksmeisterschaft Frankfurt'); -- 'District Championships Frankfurt'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (270, 'league', 'Bezirksmeisterschaft Giessen');   -- 'District Championships Giessen'
INSERT INTO Competitions (geo_area_id, type, label) VALUES (271, 'league', 'Bezirksmeisterschaft Kassel');    -- 'District Championships Kassel'

INSERT INTO Competitions (geo_area_id, type, label) VALUES ( 88, 'cup', 'DBB Pokal');              -- 'Country Cup Germany'
-- INSERT INTO Competitions (geo_area_id, type, label) VALUES (250, 'cup', 'Regionenpokal Süd');      -- 'Region Cup South' => DOESN'T EXIST IN REALITY!
INSERT INTO Competitions (geo_area_id, type, label) VALUES (258, 'cup', 'Landespokal Hessen');     -- 'State Cup Hessen'  => PROBLEM HERE! parent should be country cup Germany, but it points to Region South due to the geo areas nature
INSERT INTO Competitions (geo_area_id, type, label) VALUES (268, 'cup', 'Bezirkspokal Darmstadt'); -- 'District Cup Darmstadt'

对于常规赛(联赛),这很有效(顶级实体),但是,在倒数第二次插入比赛表时,我意识到了一个我没有预见到的问题:

有些比赛不存在由地理区域父级确定的“父级比赛”。示例:每个州的德国杯赛的资格赛球队直接进入国家级,因为没有“德国地区杯”比赛。

按照他们的逻辑,查看与比赛隔离的地理区域,我会说地理区域本身是正确表示的。只是比赛有时似乎“跳过”了地理区域。当然没有什么不可解决的,但我现在如何才能最好地适应这种情况呢?

我想到的替代方案:

  1. 为每个地区参加模拟杯比赛。 Competitions 表需要一个 BOOLEAN is_dummy 列或类似的列。在运行时必须检查这个标志,如果它是一个虚拟的地理区域的父被返回(可能递归直到找到一个地理区域或返回 NULL)。
  2. 向比赛添加另一个可选的 parent_geo_area_id。在运行时检查此字段:如果它具有非 NULL 值,则使用该值返回父地理区域(父覆盖字段),如果不使用“正常”地理区域引用的父级。 这种方法的问题是 Competitions 表已经有一个 GeoAreas 的外键,并且添加另一个基本上代表一个“重复列” - 不是吗?这不会导致以后有条件加入吗?有可能吗?

两者都在一定程度上增加了冗余,但我不知道如何做到这一点,因为“比赛跳过问题”本身会导致它。

也许还有其他选择?如果不是,您会建议哪种替代方案?为什么?

谢谢!

【问题讨论】:

    标签: mysql database-design tree parent-child entity-relationship


    【解决方案1】:

    只是有时比赛 似乎“跳过”地理区域。没有 当然无法解决,但我该怎么做 现在最好适应这种情况?

    模拟现实世界的运作方式。

    不要调整你已经知道行不通的模型。

    【讨论】:

    • 地理区域只是按照现实世界的方式建模:区域层次结构 District -> State -> Region -> Country 由所使用的运动定义。供您参考:basketball-bund.com 在那里您可以直观地看到地理区域(没有地区)。然后,如前所述,一些比赛从右到左上地理区域而不是左下。左下角的 cup 比赛不存在。这就是我需要建模的。 只有一些比赛的性质“添加”了这个“跳过功能”。地理区域本身是多年前定义的,代表了现实世界。
    • 我知道您按照现实世界中的地理区域建模方式。但你没有那样模拟比赛。每当您发现自己在考虑虚拟行或可选的父 ID 编号时,这表明您的模型完全错误。现实世界的联赛没有虚拟比赛。也许您已经为实际上并不存在的竞争层次结构建模。
    • 您的评论暗示我应该使用 Competitions 父级并完全删除 GeoAreas 父级,因为创建地理区域只是为了形成竞赛的地理层次结构。我必须考虑一下。很难。
    • 我选择了以下非常漂亮的解决方案:我保留了两列 PK 并将父 FK 添加到 Competitions 表中。通常你会得到另外两列,但在我的情况下,竞争层次结构永远无法逃脱它们的类型。这使得另一个类型列变得多余,我总是可以简单地使用当前子实体之一。因此,父 FK 将由 (parent_geo_area_id, type) 组成,并且即使该表具有多列 PK,也只添加了一列。
    猜你喜欢
    • 1970-01-01
    • 2013-08-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-05-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多