Ada*_*nch 7 mysql sql database database-design logical-operators
我想在(MySql)数据库中存储大学课程的详细信息,但我不确定如何维护模块和选择之间的关系.
基本上,课程可以有必修部分,可选模块组,选项部分,每个部分中都可以包含模块之间包含AND或OR的选项.
简单的例子:
一个60学分的课程有一些强制性的模块,组成40学分.这样就可以从可选模块组中选择20个学分.(模块本身可以持有不同数量的学分).有效; ('Mandatory module 1' AND 'Mandatory module 2'... AND'Mandatory module N') AND (40 credits from 'optional modules')
,
ANDs&ORs:
当我说上面的模块时,它可以是单个模块,也可以是"模块x或模块Y",即强制部分.(这些模块显然必须具有相同的信用权重).或者在可选部分中可能有单个模块,甚至其中一个选项可能是类似的"module x AND module y"
.
选项:
学生可能必须采用强制性模块加上n个选项中的一个,这些选项可能包含也可能不包含AND,OR和强制性和可选部分; 即'选项'具有整个课程模块选择的所有属性.选项部分将与强制或可选的其他部分进行"与"或"或"运算; 即强制性模块"加上以下选项之一".有效的选项部分就是'Option 1' OR 'Option 2'... OR 'Option N'
.
问题是当操作数可能是另一个AND/OR操作或单个模块时,如何存储所有AND和OR关系,并跟踪每个选择允许的信用量; 例如"来自以下的20个学分:"(可选模块组).
该设计相当简单,您只需要一个带有约束的递归“组”表。
Course
- ID
- Title
- Credits
Course_Group
- CourseID
- GroupID
Group
- ID
- GroupID
- Description
- AtLeastNSelections
- AtLeastNCredits
Group_Module
- GroupID
- ModuleID
Module
- ID
- Title
- Credits
Run Code Online (Sandbox Code Playgroud)
一个示例结构是
Course: 1, "Math Major", 60
Group: 1, NULL, "Core Modules", 2, 40
Course_Group: 1, 1
Group: 2, 1, "Required (5) Core Modules", 5, 25
Course_Group: 1, 1
Group_Module: (1, 1), (1, 2), (1, 3), (1, 4), (1, 5)
Module: 1, "Calculus I", 5
Module: 2, "Calculus II", 5
Module: 3, "Calculus III", 5
Module: 4, "Stats I", 5
Module: 5, "Stats II", 5
Group: 3, 1, "Required (3) Of (N) Modules", 3, 15
Course_Group: 1, 3
Group_Module: (3, 6), (3, 7), (3, 8), (3, 9), (3, 10)
Module: 6, "Number Theory", 5
Module: 7, "Bridge Adv. Math", 5
Module: 8, "Calculus IV", 5
Module: 9, "Stats III", 5
Module: 10, "Finite Math", 5
Group: 4, NULL, "Secondary Modules", 1, 20
Course_Group: 1, 4
Group: 5, 4, "Comp. Sci.", 2, 0
Course_Group: 1, 5
Group_Module: (5, 11), (5, 12), (5, 13), (5, 14), (5, 15), (5, 16)
Module: 11, "Math in Hardware", 4
Module: 12, "Math in Software", 4
Module: 13, "Programming 101", 4
Module: 14, "Algorithms 101", 4
Module: 15, "Programming I", 5
Module: 16, "Programming II", 5
Group: 6, 4, "Physics", 0, 8
Course_Group: 1, 6
Group_Module: (6, 17), (6, 18), (6, 19), (6, 20)
Module: 17, "Physics Mechanics", 4
Module: 18, "Physics Thermodynamics", 4
Module: 19, "Physics Magnetism", 5
Module: 20, "Physics Theoretical", 5
Group: 7, 4, "Gen. Ed.", 0, 0
Course_Group: 1, 7
Group_Module: (7, 21), (7, 22), (7, 23), (7, 24)
Module: 21, "Business Writing", 3
Module: 22, "Ethics", 3
Module: 23, "Aesthetics", 3
Module: 24, "Graphic Design", 3
Run Code Online (Sandbox Code Playgroud)
快速浏览一下……“数学专业”课程有两个组:“核心模块”和“辅助模块”。“核心模块”需要至少 2 名儿童且至少 40 个学分。“中学模块”需要至少 1 个孩子且至少 20 个学分。
您可以看到“核心模块”下的组的约束比“辅助模块”下的组的约束更严格。
输出上面的示例结构会是这样的。
SELECT c.Title, g.Description, m.Title FROM Course c
INNER JOIN Course_Group cg ON c.ID = cg.CourseID
INNER JOIN Group g ON cg.GroupID = g.ID
INNER JOIN Group_Module gm ON g.ID = gm.GroupID
INNER JOIN Module m ON gm.ModuleID = m.ID
WHERE c.ID = 1
ORDER BY g.GroupID, g.ID, m.Title
Run Code Online (Sandbox Code Playgroud)
因此,如果您有一门课程和模块,您可以从 Course_Group 表中获取课程的所有组,并从 Group_Module 表中获取模块所属的组。一旦您将模块放入组中,您就可以沿着 Group.GroupID 父系链检查组的约束 AtLeastNSelections 和 AtLeastNCredits,直到到达 Group.GroupID = NULL。