问题描述
嗨,我开始尝试sql和数据库设计。 我了解事物的sql方面,但是尝试绘制图表有点令人困惑。
请考虑以下业务规则:
- 见习生有姓名,见习生ID和电子邮件。
- 一个学员最多一次属于一个学员项目
- 随着时间的推移,受训人员可能会参加多个项目。
- 每个项目都有一个名称和一个项目代码。程序由单个部分运行。一节可能 运行多个项目。
- 一个项目可以有很多学员
如果受训人员一次只能完成一个项目,但是业务规则表明,随着时间的推移,他们可能会执行多个项目。以前的项目将如何保留?
有人可以向我展示多重性吗?
编辑: 抱歉,我认为它添加了我的屏幕截图:
解决方法
一个学员最多一次属于一个学员项目
这可以通过约束来表明:对于给定的学员,项目的日期永远不会重叠。
在OCL中,约束可以写为:
context Trainee inv:
self.ProjectHistory->forAll(h1,h2 |
h1<>h2 implies (h1.dateCompleted < h2.dateStarted) or
(h1.dateStarted > h2.dateCompleted))
还具有:
context ProjectHistory inv:
self.dateStarted <= self.dateCompleted
假设 dateCompleted 在项目进行时已设置为当前日期,我们知道该项目正在通过其他方式进行。
如果在项目进行中 dateCompleted 的值为0:
context ProjectHistory inv:
(self.dateStarted > 0) and
((self.dateCompleted = 0) or (self.dateStarted <= self.dateCompleted))
context Trainee inv:
self.ProjectHistory->select(dateCompleted = 0)->size() <= 1
context Trainee inv:
self.ProjectHistory
->forAll(h1,h2 |
h1<>h2 implies
if h1.dateCompleted = 0 then
h1.dateStarted > h2.dateCompleted
else
if h2.dateCompleted = 0 then
h2.dateStarted > h1.dateCompleted
else
(h1.dateCompleted < h2.dateStarted) or
(h1.dateStarted > h2.dateCompleted)
endif
endif
)
使用关联类是正确的方法。
随着时间的推移,受训人员可能会参加多个项目。
因此,任何数字,多重性0..1
必须是0..*
或快捷方式*
。
如果该规则和前一个规则被(随着时间的推移)代替,则受训者最多只能属于1个受训者项目
,倍增必须为0..1
一个部分可以运行多个项目。
因此,任何数字,多重性1..*
必须为0..*
或快捷方式*
一个项目可以有可能受训的人
可能明显是很多,所以高位数不是1。
仅具有a project have many trainees
可能意味着最小数量为,1,而对于can have
,最小数量为0而不是1。
因此,多样性最终是0..*
或快捷方式*
,而不是1..1
以前的项目将如何保留?
由于0..*
而不是0..1
的多样性,受训人员仅与进行中的项目(如果存在)没有关系
总结:
对象图示例:
您可以检查是否遵守所有规则。
在某些情况下,属性名称包含类的名称,例如 projectNam e和 traineeId ,这是没有用的,建议您删除该名称属性名称中该类的名称。
,“项目”一词不明确。标准含义是项目由工作包组成,这些工作包具有由不同项目参与者执行的各种活动/任务。这样的项目当然有开始和结束时间。
另一个“中学”的意思是“项目”在教育中,类似于定义为任务类型的作业,任何学生都可以随时开始/完成。
我的模型引用第一个(更常见的)概念。
为了表达“一个学员最多一次属于一个学员项目”的约束,必须以附加到Trainee
类的不变式(框)的形式表示,如下所示:
不使用ocl直观地描述所需语义的解决方案:
每个Trainee-Project
关联都有开始日期,但是只有Completed Trainee-Project
关联有结束日期。这很简单,这将是我们每天用英语表达的方式。那么为什么不在类图中这样做呢?这样就很容易表达,每个Trainee
最多可以有一个当前项目。通过派生端点,可以说关联的类型定义了端点的显示位置-在current project
或completed projects
中。
链接必须随时间从current Trainee-Project
更改为completed Trainee-Project
。如果您觉得这很奇怪,您可能会考虑编程语言。其中大多数不支持动态重分类。但是实际上这是现实。受训者将有一天成为一名雇员。就像一位伟大的诗人曾经说过的那样,他们正在改变课堂(据我所记得;-)
您可能会说,SQL不支持此功能。是的,但是它也不支持n:m关系。因此,无论如何,您都需要将域模型映射到SQL。因此,使您的域模型尽可能接近您的需求,并在以后考虑到SQL的映射。