数据建模:逻辑建模练习
在尝试学习数据存储艺术的过程中,我一直在尝试获取尽可能多的可靠信息。 PerformanceDBA 在以下帖子中发布了一些非常有用的教程/示例:我的数据标准化了吗? 和关系表命名约定。我已经在此处提出了该模型的子集问题。
因此,为了确保我理解他提出的概念以及我在其他地方看到的概念,我想进一步采取一两步,看看我是否掌握了这些概念。这就是这篇文章的目的,希望其他人也能从中学习。我所呈现的一切对我来说都是概念性的,是为了学习而不是将其应用到某些生产系统中。从 PerformanceDBA 那里获得一些意见会很酷,因为我使用了他的模型来开始,但我很感谢任何人提供的所有意见。
由于我对数据库,尤其是建模很陌生,我将第一个承认,由于缺乏该主题的专业知识,我可能并不总是提出正确的问题,清楚地解释我的想法,或使用正确的措辞。因此,请记住这一点,如果我偏离了轨道,请随时引导我走向正确的方向。
如果对此有足够的兴趣,我想从逻辑阶段到物理阶段来展示该过程的演变,并在 Stack 上分享。不过,我将保留逻辑图的这条线索,并为附加步骤开始新的线索。根据我的理解,我最终将构建一个 MySQL 数据库来运行一些测试,看看我的想法是否真正有效。
以下是我想要在此概念模型中捕获的内容的列表。 针对 V1.2 进行编辑
- 这样做的目的是列出乐队、其成员以及他们将出席的活动,并提供音乐和其他待售商品,
- 会员将能够匹配与朋友一起
- 会员可以对乐队、他们的音乐和活动发表评论。
- 每个会员只能对某一特定商品发表一条评论,但他们可以编辑自己的评论并且历史记录将被保留。
- 乐队成员将有机会在有关与他们相关的乐队的评论中撰写一条评论。总的来说,作为一个乐队,每条评论只允许发表一条评论。
- 然后,成员可以对所有评论和评论进行评分,但每个给定实例只能评分一次
- 会员可以选择他们最喜欢的乐队、音乐、商品和活动。
- 乐队、歌曲和活动将被分类为他们所属的流派类型,然后进一步细分为如有必要,可使用子流派。乐队或活动可以属于多个流派/子流派组合。
- 特定乐队的活动日期、时间和地点将被公布,成员可以表明他们将参加该活动。一场活动可以由多个乐队组成,并且多个活动可以在同一天在一个地点举行
- 。每一方都将绑定到至少一个地址,并且应维护地址历史记录。每一方还可以一次绑定到多个地址(即账单、运输、物理)。
- 将存储乐队、乐队成员和一般成员的配置文件。
就这样,也许有点复杂,但随着流程的发展和社区的投入,对于许多人来说可能是一个很好的学习工具。有什么意见吗?
编辑 v1.1 响应 PerformanceDBA
U.3) 这意味着数据库中没有除 Band 商品以外的商品。正确吗? 这是我最初的想法,但你让我开始思考。也许该网站想要出售自己的商品,甚至是乐队的其他商品。不确定为此制作一个模组。是否需要对目录部分进行整个重新设计,或者仅需要重新设计与乐队之间存在的识别关系? 尝试制作一个模组来销售完整的专辑或歌曲。无论哪种方式,它们都是电子格式,仅供下载。这就是为什么我将专辑列为由歌曲组成而不是两个单独的实体。
U.5) 我理解您提到的与Favorite 的循环关系。我想了解这一点“它是一个具有某种形式的分化(FavoriteType)的实体,它可以识别其治疗”,但我不清楚如何做到这一点。我在这里缺少什么?
u.6) “业务规则这可能是您唯一薄弱的领域。”
感谢您的诚实回复。我将重新解决这些问题,但我希望首先通过我发回给您的回复来消除我头脑中的一些困惑。
Q.1) 是的,我希望接受、拒绝和阻止。我不确定您指的是这将如何改变逻辑模型?
Q.2) 一个人不一定是用户。他们只能作为乐队成员而存在。这就是你问的吗?
小问题
零个、一个或更多…哎呀我承认我在构建模型时忘记了这一点。我按原样提交此版本,并将在未来版本中解决。我需要阅读更多有关约束检查的内容,以确保我理解事情。
M.4) 取决于您是否设想将来使用 OrderPurchase。 您能详细解释一下您在这里的意思吗?
编辑 V1.2 为了响应 PerformanceDBA 的输入...
经验教训。
- 我混合了识别/非识别和基数(即流派/子流派)的概念,并且不一致地这样做使事情变得更糟。
- 逻辑图中不需要关联表,因为可以描述它们的多对多关系,然后在物理模型中进行扩展。
- 我忽略了很多关系中的基数
- 使用有效的动词短语来阅读关系的重要性,以确保我正在建模我想要完成的任务。
U.2) 在此模型的概念中,仅需要跟踪场地作为事件的位置。无需收集更多数据。话虽这么说,活动将在给定的活动日期举行,并将在场地举办。场地将举办多个活动,并且可能在给定日期举办多个活动。在我的新模型中,我的想法是 EventDate 已经与 Event 绑定在一起。因此,Venue 不需要与 EventDate 建立关系。不过,您在 U.2 下列出的第 5 个和第 6 个项目符号让我质疑我的想法。我在这里错过了什么吗?
U.3) 是时候将 Item 和 Band 之间的链接移至 Item 和 Party 了吗?根据目前的设计,我认为不可能销售与您提出的乐队无关的商品。
U.5) 我根据您的输入离开,而不是使其成为离散的超类型/子类型关系,因为我没有看到这种类型的汇总有什么好处。
其他修订
AR.1) 在完成FavoriteItem的练习后,我觉得要审核的Item需要多对多的关系,因此需要指出。必要的?
好吧,我们开始 v1.3
我花了几天时间处理这个问题版本,来回我的设计。一旦逻辑过程完成,因为我想看看我是否走在正确的轨道上,我将深入了解我所学到的知识以及作为初学者在经历这个过程时遇到的麻烦。这个版本的重点是它需要添加一些键来帮助我了解我过去缺少的内容。事实证明,完成制作矩阵的过程也有很大帮助。无论如何,如果没有 PerformanceDBA 提供的输入,我仍然会是一个在黑暗中迷失的灵魂。谁知道我现在的设计可能会再次证明我仍然是这样,但我学到了很多东西,所以我知道我手里至少有一个手电筒。
此时此刻,我承认我仍然对识别和非识别关系感到困惑。在我的模型中,我必须使用非空值的非标识关系来加入我想要建模的关系。在阅读了有关该主题的大量内容后,似乎在该主题上存在很多分歧和优柔寡断,因此我做了我认为在我的模型中代表正确事物的事情。何时强制(认同),何时自由(非认同)?有人有意见吗?
编辑 V1.4
好的,接受了 V1.3 输入并清理了内容对于此 V1.4
目前正在开发 V1.5 以包含属性。
编辑 V1.6
好的,我已经有一段时间没有发布了在这里,但该项目的工作仍在进行中。我现在发布 V1.6,其中包含与上次发布 V1.4 相比的一些更改。该版本展示了 Keys 的进一步发展。它仍然不包括属性或任何 AK 或 IE。我已经开始研究物理模型,并使用它来帮助处理属性,并尝试阐明我在定义 AK 和 IE 时遇到的问题。逻辑模型的下一篇文章将包括这些键和属性。
In trying to learn the art of data storage I have been trying to take in as much solid information as possible. PerformanceDBA posted some really helpful tutorials/examples in the following posts among others: is my data normalized? and Relational table naming convention. I already asked a subset question of this model here.
So to make sure I understood the concepts he presented and I have seen elsewhere I wanted to take things a step or two further and see if I am grasping the concepts. Hence the purpose of this post, which hopefully others can also learn from. Everything I present is conceptual to me and for learning rather than applying it in some production system. It would be cool to get some input from PerformanceDBA also since I used his models to get started, but I appreciate all input given from anyone.
As I am new to databases and especially modeling I will be the first to admit that I may not always ask the right questions, explain my thoughts clearly, or use the right verbage due to lack of expertise on the subject. So please keep that in mind and feel free to steer me in the right direction if I head off track.
If there is enough interest in this I would like to take this from the logical to physical phases to show the evolution of the process and share it here on Stack. I will keep this thread for the Logical Diagram though and start new one for the additional steps. For my understanding I will be building a MySQL DB in the end to run some tests and see if what I came up with actually works.
Here is the list of things that I want to capture in this conceptual model. Edit for V1.2
- The purpose of this is to list Bands, their members, and the Events that they will be appearing at, as well as offer music and other merchandise for sale
- Members will be able to match up with friends
- Members can write reviews on the Bands, their music, and their events.
- There can only be one review per member on a given item, although they can edit their reviews and history will be maintained.
- BandMembers will have the chance to write a single Comment on Reviews about the Band they are associated with. Collectively as a Band only one Comment is allowed per Review.
- Members can then rate all Reviews and Comments but only once per given instance
- Members can select their favorite Bands, music, Merchandise, and Events
- Bands, Songs, and Events will be categorized into the type of Genre that they are and then further subcategorized into a SubGenre if necessary. It is ok for a Band or Event to fall into more then one Genre/SubGenre combination.
- Event date, time, and location will be posted for a given band and members can show that they will be attending the Event. An Event can be comprised of more than one Band, and multiple Events can take place at a single location on the same day
- Every party will be tied to at least one address and address history shall be maintained. Each party could also be tied to more then one address at a time (i.e. billing, shipping, physical)
- There will be stored profiles for Bands, BandMembers, and general members.
So there it is, maybe a bit involved but could be a great learning tool for many hopefully as the process evolves and input is given by the community. Any input?
EDIT v1.1
In response to PerformanceDBA
U.3) That means no merchandise other than Band merchandise in the database. Correct ?
That was my original thought but you got me thinking. Maybe the site would want to sell its own merchandise or even other merchandise from the bands. Not sure a mod to make for that. Would it require an entire rework of the Catalog section or just the identifying relationship that exists with the Band?
Attempted a mod to sell both complete albums or song. Either way they would both be in electronic format only available for download. That is why I listed an Album as being comprised of Songs rather then 2 separate entities.
U.5) I understand what you bring up about the circular relation with Favorite. I would like to get to this “It is either one Entity with some form of differentiation (FavoriteType) which identifies its treatment” but how to is not clear to me. What am I missing here?
u.6) “Business Rules This is probably the only area you are weak in.”
Thanks for the honest response. I will readdress these but I hope to clear up some confusion in my head first with the responses I have posted back to you.
Q.1) Yes I would like to have Accepted, Rejected, and Blocked. I am not sure what you are referring to as to how this would change the logical model?
Q.2) A person does not have to be a User. They can exist only as a BandMember. Is that what you are asking?
Minor Issue
Zero, One, or More…Oops I admit I forgot to give this attention when building the model. I am submitting this version as is and will address in a future version. I need to read up more on Constraint Checking to make sure I am understanding things.
M.4) Depends if you envision OrderPurchase in the future.
Can you expand as to what you mean here?
EDIT V1.2
In response to PerformanceDBA input...
Lessons learned.
- I was mixing the concept of Identifying / Non-Identifying and Cardinality (i.e. Genre / SubGenre), and doing so inconsistently to make things worse.
- Associative Tables are not required in Logical Diagrams as their many-to-many relationships can be depicted and then expanded in the Physical Model.
- I was overlooking the Cardinality in a lot of the relationships
- The importance of reading through relationships using effective Verb Phrases to reassure I am modeling what I want to accomplish.
U.2) In the concept of this model it is only required to track a Venue as a location for an Event. No further data needs to be collected. With that being said Events will take place on a given EventDate and will be hosted at a Venue. Venues will host multiple events and possibly multiple events on a given date. In my new model my thinking was that EventDate is already tied to Event . Therefore, Venue will not need a relationship with EventDate. The 5th and 6th bullets you have listed under U.2) leave me questioning my thinking though. Am I missing something here?
U.3) Is it time to move the link between Item and Band up to Item and Party instead? With the current design I don't see a possibility to sell merchandise not tied to the band as you have brought up.
U.5) I left as per your input rather than making it a discrete Supertype/Subtype Relationship as I don’t see a benefit of having that type of roll up.
Additional Revisions
AR.1) After going through the exercise for FavoriteItem, I feel that Item to Review requires a many-to-many relationship so that is indicated. Necessary?
Ok here we go for v1.3
I took a few days on this version, going back and forth with my design. Once the logical process is complete, as I want to see if I am on the right track, I will go through in depth what I had learned and the troubles I faced as a beginner going through this process. The big point for this version was it took throwing in some Keys to help see what I was missing in the past. Going through the process of doing a matrix proved to be of great help also. Regardless of anything, if it wasn't for the input given by PerformanceDBA I would still be a lost soul wondering in the dark. Who knows my current design might reaffirm that I still am, but I have learned a lot so I am know I at least have a flashlight in my hand.
At this point in time I admit that I am still confused about identifying and non-identifying relationships. In my model I had to use non-identifying relationships with non nulls just to join the relationships I wanted to model. In reading a lot on the subject there seems to be a lot of disagreement and indecisiveness on the subject so I did what I thought represented the right things in my model. When to force (identifying) and when to be free (non-identifying)? Anyone have inputs?
EDIT V1.4
Ok took the V1.3 inputs and cleaned things up for this V1.4
Currently working on a V1.5 to include attributes.
EDIT V1.6
Okay, it has been some time since I have posted on here but the work on this project is still ongoing. I am posting V1.6 now which includes a number of changes from the last posting of V1.4. This version shows the further evolution of the Keys. It still does not include the attributes or any AK's or IE's. I have started working on the physical model and used that to help work through the attributes and to try and shed some light on the problems I am having with defining the AK's and IE's. The next posting of the Logical Model will include these keys and the attributes.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
...第二部分
V1.3 和响应
所有问题要么都是小问题,要么与您正在学习的新步骤相关。
标识符与 Id 列
我不会在这里给您完整的概述,因为我已经发布了至少 20 次有关
Id
列如何破坏数据库并剥夺关系数据库的信息力量。我将仅在这个问题的背景下处理这个问题。这是示例,请先详细检查问题嗯>。请注意,马克很有能力,但完全陷入困境。 然后阅读我的答案,然后查看数据模型。 (请现在就这样做,它提供了上下文)
这个想法是或者将数据建模为数据,我们正在这样做,您最终将得到一个数据库,xor< /em> 将
Id
列粘贴在所有移动的内容上,这会阻碍建模练习和规范化,最终您将得到一堆相互“链接”的电子表格,其中存在大量重复且没有性能。< /p>因此,从所有表中删除
[Table]Id
形式的所有列(保留迁移的键,它们是正确的),除了以下表(这些是主要标识符,反映在整个数据库中。请注意 ERwin 将如何更正所有子表、孙表等:聚会
地址
项目
关系/IDEF1X 标识符
您正在学习标识符。这些是自然键。用户使用的密钥,或已作为外键从父项迁移到子项的密钥。因此,这些不仅可以识别关系,还可以识别孩子。你的姓氏不仅告诉我你的情况,还告诉我你父亲的情况,而且你是你父亲的儿子。想让它独一无二吗?没问题,只需添加名字即可。
您一直在阅读我的答案,查看我的数据模型,然后添加标识符到您的模型中。它*比这容易得多。 ERwin(因为它实现了 IDEF1X)会为您做到这一点。
参加派对、乐队和个人。参与方的标识符是
PartyId
(好吧,那是代理键,不是自然键;但是自然键
Lastname, FirstName,BirthDate
等很长,如果我们用它作为主键,它会迁移到孩子、孙子、曾孙,这是不可取的,所以我们添加一个短代理键,并将其设为主键)当您创建ERwin中的子类型,并注明Relation,它会自动将
PartyId
放入Band和Person中,作为PK;它会将其标记为“(FK)”。 (注:我在模型中使用粗体表示(FK)。)就这样,你就完成了。 Party::Band 为 1:0-1,Band 主键为
PartyId
。因为它是子类型,ERwin 将确保关系是识别,因此父 PK 最终出现在子 PK 中,并且从属子项具有圆角。如果不涉及子类型,则结果是相同的,只是关系可能不是 1::0-1,而可能是 1::1-n。在这种情况下,您需要添加另一个元素以使其唯一,例如 f
FirstName
或SequenceNo
并且您必须向 ERwin 表明您想要一个识别关系。 (如果不这样做,那么它就是一个普通的 FK,列将位于该行下方;表格将是独立的;角是正方形的)。
如果在某个时候您决定使用这些 FK 列来形成 PK,您只需单击关系并将其从“非识别”更改为“识别”即可;列将移动到该线上方;角将是圆的。
角色
现在进行下一步。我们知道 Band::Party 是 1::1;该 Band 是 Party 的子级;
Band.PartyId
是完美的 PK(不需要Id
列)。对于人来说也是如此。但它们都是愚蠢的名字,或者换句话说,Band实际上是与Person不同的Role,而且它们都是一个Party。所以我们要明确角色。在 Band 中,我们希望调用
PartyId
、BandId
来反映其角色。编辑子类型符号与子类型(而不是表)之间的关系。在对话框中,将 RoleName 填写为BandId
。就是这样。你已经完成了。因此,以下内容从...更改为:
因此...
删除所有
[Table]Id
列将使以下表格失去 PK。现在,添加Name
列作为 PK。您可以稍后告诉我用户想要什么自然键,这些表的标识符:活动
类型
PartyAddress 是我上面讨论的一个示例(即正确建模)。它没有
PartyAddressId
。PartyId
和AddressId
一起构成 PK。两种关系都是认同的。识别与非识别关系
是的。不幸的是,如今任何拥有键盘和调制解调器的人都可以“发布”。人们发表意见作为事实;他们发表关于他们一无所知的主题的废话。这让那些试图学习的人感到困惑。
这是科学,不是魔法或巫术,也不是观点。
学习时,只阅读定义,只听那些清楚地传递科学的人的声音(而不是任何混淆或将科学视为一门艺术或受制于观点的人)。我们正在学习事实、物理定律,而不是关于这些定律的观点;这些法律对地球上的每个人都是一样的。你无法向那些认为事实就是观点的人学习。
让我们从顶部开始:
关系是定义标准(使子项独立/从属),而不是相反。
关系始终是子级中的 FK、父级 PK 的 FK。
在识别关系中,FK 是 PK(或 PK 的第一部分,其中 PK 是复合键)。子表是一个依赖表。
在非识别关系中,FK 是非 PK 列,并且子项是独立(它可能会被其他关系强制进入依赖关系)。
所有子类型都具有来自父类型的识别关系。否则它们就不是子类型,它们将独立于超类型。
所有 1:0-1 关系都具有识别性。
[Table]Id
键的原因。这就是为什么在每个电子表格上粘贴
Id
列的行为会阻碍对数据的理解,从而阻碍对数据的任何建模。执行关系/IDEF1X/ERwin 风格:
您想要一个实体,请绘制一个实体。命名它。除非它是画布上的第一个实体,否则不要添加键。
现在考虑它的关系。您已经建模的实体如何与这个新实体相关?绘制该关系(绘制父子关系)。
当然,它默认为“识别”,因为(等等)关系型数据库中的大多数关系都是“识别”。父 PK 放置在子 PK 中。
如果您认为,不,不,我希望这是独立的,那么您最好有一个充分的理由。这里的关键问题是,这个实体是否完全独立存在,是否存在于其他独立实体的上下文之外? AFAIC,您的模型中有五个:
地址
聚会
项目
活动
类型
每个其他实体仅存在于这些独立实体之一的上下文中。因此你画出了识别关系,因此它们都是依赖关系。
回想一下,我们之前将 Item 作为独立项;然后我们有了一种新形式的 Item;这使得旧的 Item,BandItem;这使得 BandItem 依赖于新 Item。
我们在
ItemId
中有一个很棒的标识符,它不仅在(当时的)Item 集群中携带,而且在整个 OrderItem、Review 等中都携带。我们改变了 Item 的上下文(创建了一个更高的) order Item),并且由于识别关系,该随后被完全迁移,并且新的 BandItem 在其上下文中被迁移。
新的
ItemId
仍然是一个很棒的标识符。BandItemId
与ItemId
完全相同,但扮演着特定的角色,它是ItemId
的子集/子类型。但在这个阶段,不是一个
Id
列,而是一些有意义的标识实体的列。事件.名称
,客户.Code
。没有人会将客户识别为数字 123456,不,他们会想到“IBM”、“3M”等。稍后,随着模型的进展,我们将确保我们拥有真正好的密钥;现在对于新实体,我们关心它有一个标识符。异常。对于地址、聚会、项目,您知道在 V1.0 中您将拥有数百万、数千、数千个;这些是将在整个数据库中迁移的主要标识符;真正的PK是很漫长的;并且您需要一个短代理密钥作为 PK;所以你从一开始就设定了这一点,我没有对你提出任何异议。
如果您已准备好域,则 INT、INT 或 SMALLINT、SMALLINT。
否则
名称
,CHAR(30)。下一步是完成新实体的PK。如果来自父级的基数是1::n,则它已经具有父级的PK,只需添加一个元素以使PK唯一。我们来看看订单。它已经具有
PartId
,因此OrderNo
可以位于PartyId
内。只需将 PK 列的顺序更改为(1) PartyId, (2) OrderNo
。唯一一次我们做一点强制,是当形成 PK 的列数变得太多,或者 PK 的总宽度变得太宽时,才能作为 FK 迁移到子级中。然后,只有到那时,我们才会创建一个
[Table]Id
形式的附加代理键(它们始终是附加的,我们不能失去真正的 PK 或唯一性,因为它支持其他要求)。AFAIC,这个神奇的数字是七(实际上,对于很多东西来说都是神奇的“否”;甚至这个项目也显示为数字七),最大宽度是 30 字节。这是从一开始就通过地址(已经高度优化)、聚会(否则为 64 字节)、项目(超过 30 字节)来完成的。
如果我们要打破内在的关系力量,我们需要承受这种关系力量本身非常糟糕的痛苦,没有其他原因。在您的模型中甚至没有接近这一点。
审核集群
您已经完成了非常好的工作,因此请将此视为下一步进展。基本上你有两个选择,当然我们正在将其与项目集群进行比较/关联。
按原样使用 Review 集群。我们需要 SongReview 和 AlbumReview。并摆脱 ItemReview(它封装了所有 Items,这意味着我们要加倍)。我以为我们排除了非乐队商品的评论。
允许非 BandReview 与任何 BandItem 有关,例如。将 ItemReview FK 从 Item 更改为 BandItem。它封装了 ItemReview 中的所有 BandItem。摆脱 PerformanceReview。
颜色
很高兴您采用了我的配色方案。
意义,视觉相关性,不会出现在一个小模型中(我的大多数模型都是如此);它只出现在像您这样的较大型号上。
因为您在 V1.3 方面做得非常出色,所以我创建了 为您准备的 ERD。实际上,IDEF1X 表示法 文档值得再次阅读,它非常简洁,而且我被告知,当人们在建模之后阅读它时,会从中获得更多价值。我需要知道的是,自然层次和颜色是否对你有帮助。
这刚刚完成了实体级逻辑。
您可以继续逻辑、关键级别(唯一的属性是 FK,我们知道它们是什么)。但请随意开始识别属性(在这种情况下,显示属性级别)。
可选列
U.1) 可选父项已重新进入模型。
PartyAddress 已发货,因为订单
不可为 Null。如果您打算将送货地址建模为可选,那么您需要一个 OrderShipAddress 实体,它是 Order 的子实体,基数为 1::0-1。
Null(可选列)就像遍布全身的癌症,Nullable FK(可选父项)是五岁之前孤儿的喉癌。
.
这是处理任何可选列的基本方法,不限于 FK(可选父级),例如此处。
次要
M.11)这些在 V1.2 中是正确的
评论::评论为1::0-1
BandMember:: 注释是 1:0-n
M.12) Event::Person 是 n::n (并且列不会在逻辑级别显示)
V1.4 和响应
非常好的进展。您对标识符、密钥满意吗?
U.8)(如果您首先执行此操作,其余部分将很容易遵循。) ERwin 限制。恭喜,您生成的模型已达到 ERwin 逻辑建模能力的极限。需要明确的是,这并不是真正的限制,因为它在物理模型中得到了解决,当然它也不是 IDEF1X 或关系数据库中的限制。但现在,在逻辑学院,它会干扰你的学习和进步。
在 BandItem 中,我们希望 PK 为 (BandItemId, BandId)。但 ERwin 不允许这样做,因为它说子类型 PK 必须是超类型 PK,仅此而已。实际上,只要超类型 PK 是主导标识符,其他识别关系也是可以接受的。要解决此问题:
删除子类型符号
创建两个识别关系Item::FloorItem和Item::BandItem
我们必须设为非识别的关系现在可以是识别的。
ERwin 现在会将迁移的 PK 解析为 FK,而不会重复。
是的,将角色放回原处。
) 现在我明白您要对 Review 集群执行什么操作,所以首先,我要说您已经正确建模了,一直到评级。
M.13) Order::OrderShipAddress 是 1::0-1,正确。
PartyAddress::Order 是 1::0-n,正确
因此,送货地址应为 PartyAddress::OrderShipAddress 1::0-n
M.14) 付款方式目前每个订单仅允许一次付款,这可能是您所需要的,但关系是 1::1-n。如果需要更多,则在 PK 中添加 SequenceNo。
M.15) 类型很好。但 SubGenre 需要 PK 中的某些东西来允许多个 Genre。我现在将 Genre.Name 更改为 Genre.Genre,并将 SubGenre 添加到 SubGenre PK。
M.16) 场地现在需要一个 PK 的名称。如果您准备好使用更好的键,则 ShortName 和 Name 将作为属性向下移动。
Q.4) 确认。由于我们在 Order 和 PK (PartyId, OrderNo) 中有一个识别关系,因此 OrderNo 是 PartyId 中的序号,对吗?
选择 V1.5。包括一些属性。识别它们的最佳方法是启动一个功能模型(现在与它并排使用数据模型)或至少处理所有屏幕的所有功能。
... Part II
V1.3 and Response
All the issues are either minor, or relate to the new step you are learning.
Identifiers vs Id columns
I am not going to give you a full rundown here, as I have posted at least 20 times about how
Id
columns cripple a database and rob it of Relational Power. I will deal with the issue in the context of this question only.Here is an example, check the question in detail first. Note that Mark is quite capable, but completely stuck. Then read my answer, then look at the Data Model. (Please do that now, it provides context)
The idea is either model the data, as data, which we are doing, and you will end up with a database, xor stick
Id
columns on everything that moves, which obstructs the modelling exercise and Normalisation, and you will end up with a bunch of spreadsheets "linked" to each other with massive duplication and no performance.Therefore, remove all columns of the form
[Table]Id
from all tables (leave the Migrated Keys alone, they are correct), except the Following tables (these are the major Identifiers, reflected throughout the database. Note how ERwin will correct all child, grandchild, etc. tables:Party
Address
Item
Relational/IDEF1X Identifiers
You are learning about Identifiers. These are the Natural Keys. Either Keys that the user uses, or Keys that have been Migrated from a parent to a child as Foreign Keys. These are therefore not only identifying the Relation but also Identifying the child. Your last name tells me not just about you, but also about your father, and also that you are your father's son. Want to make that unique ? No problem, just add a first name.
You have been reading my answers, looking at my Data Models, and then adding Identifiers to your model. It is *much easier than that. ERwin (since it implements IDEF1X) does that for you.
Take Party, Band and Person. The Identifier for Party is
PartyId
(ok, that is a Surrogate Key, not a Natural key; but the Natural Key
Lastname, FirstName,BirthDate
, etc. is very long, if we use that as the Primary Key, it would be Migrated to the children, grandchildren, great-grandchildren, which is not desirable, so we add a short Surrogate Key, and make that the Primary Key)When you create the subtypes in ERwin, and indicate the Relation, it will automatically place
PartyId
in Band and Person, as the PK; it will mark it as "(FK)". (Note: I use bold font to denote (FK) in my models.)That's it, you are done. Party::Band is 1:0-1, Band Primary Key is
PartyId
. Because it is a Subtype, ERwin will ensure the Relation is Identifying, and therefore the parent PK ends up in the child PK, and the Dependent child has round corners.If subtypes were not involved, it would be the same, except the Relation may not be 1::0-1, it may be 1::1-n. In which case, you need to add another element to make it unique, such as f
FirstName
, orSequenceNo
And you have to indicate to ERwin that you want an Identifying Relation. (If you don't then it is a plain FK, and the columns will be below the line; the table will be Independent,; the corners square).
And if at some point you decide to use those FK columns to form the PK, you simply click on the Relation and change it from Non-identifying to Identifying; the columns will be moved above the line; the corners will be round.
Role
Now for the next step. We know that Band::Party is 1::1; that Band is a child of Party; that
Band.PartyId
is the perfect PK (noId
column is required). Same for Person. But they are silly names, or put another way, Band is actually a different Role to Person, and they are both a Party. So we want to identify the Role clearly.In Band, we would like to call
PartyId
,BandId
, to reflect its Role. Edit the Relation, between the subtype symbol and the child, not the table. In the dialogue, fill in the RoleName asBandId
. That's it. You are done.Thus the following change from ... to:
Consequently ...
Removing all the
[Table]Id
columns will leave the following tables without a PK. For now, add aName
column as the PK. You can tell me later what the user would like for a natural key, an Identifier for these tables:Event
Genre
PartyAddress is an example (ie. modelled correctly) of what all I have discussed above. It had no
PartyAddressId
.PartyId
andAddressId
together form the PK. Both Relations are Identifying.Identifying vs Non-identifying Relations
Yes. Unfortunately, anyone with a keyboard and a modem can "publish" these days. People post opinions as facts; they post nonsense about subjects they are clueless about. This confuses people who are trying to learn.
It is science, not magic or a black art, not opinion.
When learning, read only definitions, and listen only to people who clearly transfer the science (not to anyone who is confused or treats the science like it is an art or that it is subject to opinion). We are learning facts, laws of physics, not opinions about the laws; the laws work the same for everyone, across the planet. You can't learn from someone who thinks a fact is an opinion.
Let's take it from the top:
The Relation is the defining criteria (renders the child Independent/Dependent), not the other way round.
A Relation is always an FK in the child, of the parent PK.
In an Identifying Relation, that FK is the PK (or the first part of the PK, where the PK is a composite key). And the child is a Dependent table.
In a Non-Identifying Relation that FK is a non-PK column, and the child is Independent (it may be forced into Dependence by some other Relation).
All Subtypes have Identifying Relations from the Supertype. Otherwise they would not be Subtypes, they would be Independent of the Supertype.
All 1:0-1 Relations are Identifying.
[Table]Id
keys.That is why the act of sticking
Id
columns on every spreadsheet prevents understanding of the data, and therefore any modelling of it.Do it Relational/IDEF1X/ERwin style:
You want an Entity, draw an Entity. Name it. Unless it is the first entity on the canvas, do not add keys.
Now consider its Relations. How do the Entities you have already modelled relate to this new Entity ? Draw that Relation (Relations are drawn Parent-to-child).
Of course, it defaults to Identifying, because most Relations in a (wait for it) Relational Database are Identifying. The parent PK is placed in the child PK.
If you think, no, no, I want this to be Independent, then you better have a good reason. The key question here is, does this entity exist completely on its own, does it exist outside the context of other Independent entities ? AFAIC, there are five in your model:
Address
Party
Item
Event
Genre
Every other entity exists only within the context of one of these Independent Entities. Thus you drew Identifying Relations, and thus they are all Dependent.
Recall, we had Item as Independent earlier; then we had a new form of Item; which made the old Item, BandItem; which made BandItem Dependent on the new Item.
We had a great Identifier in
ItemId
, which was carried not only in the (then) Item cluster but throughout, in OrderItem, Review, etc.We changed the context of Item (created a higher order Item), and due to the Identifying Relations, that was then Migrated throughout, and the new BandItem was Migrated in its context.
The new
ItemId
continues to be a great Identifier.BandItemId
is exactlyItemId
, but plays a particular Role, it is a subset/subtype ofItemId
.But at this stage, not an
Id
column, something meaningful that identifies the entity.Event.Name
,Customer.Code
. No human being identifies a Customer as number 123456, no, they think of "IBM", "3M", etc. Later on, as the model progresses, we will make sure we have really good Keys; right now with the new Entity, we care that it has an Identifier.Exception. For Address, Party, Item, you knew at V1.0 you were going to have millions, thousands, thousands of them; that these were major Identifiers that would be MIgrated throughout the database; that the true PK was very long; and that you needed a short Surrogate Key as the PK; so you set that up from the outset, and you got no argument from me.
If you are ready for Domains, then INT, INTor SMALLINT, SMALLINT.
Otherwise
Name
, CHAR(30).The next step is to finish the PK on the new entity. If the cardinality from the parent is 1::n, it already has the PK of the Parent, just add an element to make the PK unique. Let's look at Order. It already has
PartId
, soOrderNo
can be withinPartyId
. Just change the order of the PK columns to(1) PartyId, (2) OrderNo
.The only time we do a little bit of forcing, is when the number of columns forming the PK becomes too many, or the total width of the PK becomes too wide, to Migrate as an FK into the children. Then, and only then, we create an additional Surrogate Key of the form
[Table]Id
(they are always additional, we can't lose the real PK or the uniqueness, because it supports other requirements).AFAIC, that magic number is seven (magic no for a many things, actually; even this item appears as number seven), and that maximum width is 30 bytes. That was done from the outset with Address (already highly optimised), Party (otherwise 64 bytes), Item (over 30 bytes).
If we are going to break the intrinsic Relational power, we need the pain of carrying that Relational power itself to be really bad, and for no other reason. Not even approaching that in your model.
Review Cluster
You've done a very good job, so consider this as the next progression. Basically you have two options, and of course we are comparing/relating this to the Item cluster.
Going with the Review cluster as is. We need a SongReview and an AlbumReview. And get rid of ItemReview (that encapsulates all Items, which means we are doubling up). I thought we were excluding Reviews for non-Band Items.
Allow the non-BandReview to be about any BandItem, eg. change the ItemReview FK from Item to BandItem. That encapsulates all BandItems in ItemReview. Get rid of PerformanceReview.
Colour
It is great that you have adopted my colour scheme.
The meaning, the visual relevance, does not show up in a tiny model (most of my models on SO); it only shows up on larger models such as yours.
Because you have done such a great job with V1.3, I have created an ERD for you. Actually, the IDEF1X Notation document is worth reading again, it is very condensed, and I am told that people get more value out of it when they read it after modelling something. What I need to know is, whether the Natural Hierarchy and the Colour do anything for you.
That's just finishing off the Entity level Logical.
You can continue with the Logical, Key level (the only Attributes are FKs, and we know what they are). But feel free to start identifying Attributes (in which case, show the Attribute Level).
Optional Column
U.1) An Optional Parent has crept back into the model.
PartyAddress is shipped for Order
is not Nullable.If you intended to model that the shipping address is optional, then you need an OrderShipAddress Entity, which is a child of Order, and the cardinality is 1::0-1.
Nulls (optional columns) are like a cancer collecting all over the body, Nullable FKs (optional parent) are cancer of the throat in an orphan before the age of five.
.
That's the basic method to handle any optional column, not limited to one that is an FK (optional parent) such as here.
Minor
M.11) These were correct in V1.2
Review::Comment is 1::0-1
BandMember:: Comment is 1:0-n
M.12) Event::Person is n::n (and the columns will not show at the logical level)
V1.4 and Response
Very good progress. Are you happy with the Identifiers, the Keys ?
U.8) (If you do this first, the remainder will follow easily.) ERwin Limitation. Congratulations, you have produced a model that has reached the limitations of ERwin's capability in Logical modelling. To be clear, this is not really a limit, in that it gets resolved in the Physical Model, and of course it is not a limitation in IDEF1X or Relational Databases. But right now, at the Logical, it interferes with your learning and progress.
In BandItem we want the PK to be (BandItemId, BandId). But ERwin won't allow it because it says a Subtype PK must be the Supertype PK and nothing but. Actually, as long as the Supertype PK is the leading Identifier, another Identifying Relation is acceptable. To work around this:
drop the subtype symbol
create two Identifying Relations Item::FloorItem and Item::BandItem
The Relations that we had to make Non-identifying can now be Identifying.
ERwin will now resolve the Migrated PKs as FKs, without duplication.
Yes, chuck the Roles back in.
U.9) Now I understand what you are trying to do with the Review cluster, so first, let me say that you have modelled it correctly, all the way down to Rating.
M.13) Order::OrderShipAddress is 1::0-1, correct.
PartyAddress::Order is 1::0-n, correct
Therefore the Shipping Address should be PartyAddress::OrderShipAddress 1::0-n
M.14) Payment currently allows only one payment per Order, which may be what you require, but the relation is 1::1-n. If you need more, then add a SequenceNo to the PK.
M.15) Genre is fine. But SubGenre needs something in the PK to allow more than one Genre. I would now change Genre.Name to Genre.Genre, and add SubGenre to the SubGenre PK.
M.16) Venue needs a Name for a PK for now. If you are ready for better keys, then ShortName, and Name moves down as an attribute.
Q.4) Confirming. Since we have an Identifying Relation in Order, and the PK (PartyId, OrderNo) therefore OrderNo is a sequential number within PartyId, correct ?
Go for V1.5. Include some Attributes. The best way to identify them is to either start a Function Model (and now work the Data Model side-by-side with it) or at least work through all the functions for all the screens.
方法
我将介绍具体细节,但我将完全介绍一两个主题领域,而不是全部。您可以选择它并将其应用到所有主题领域。
我还没有对核心主题领域做出回应,因为我们仍在处理识别实体问题。当这个问题解决后,
评论
等就会变得更容易;交易实体依赖于识别实体。方向
D.1) 我知道我说过我需要查看整个模型。有一个例外。历史数据、临时数据或审核数据(例如编辑和存储的版本)。在这个早期阶段,它们可以被搁置;在逻辑模型完成之前实施。这是认识到(a)它们是某个父项的简单依赖项(b)需要首先根据所有其他表对父项进行建模,以及(c)排除不必要的复杂性,从而使我们能够专注于相关的场地。
Has/Had
)。现在请使用现在时,因为重点是建模,而不是归档。未解决
U.1) 可选父级
这是完全不允许的。不仅仅是 IDEF1X,而是任何诚信概念。如果定义了 FK Reference,则必须有一个 Parent。为了允许可选的父项,必须删除(或不实施)FK 参考。根据定义,这样的条件将排除结果作为“关系数据库”的资格。例如。
地址:订单
。订单
必须有地址
;这与标准要求问题是分开的。。
U.2) 事件
Party::PartyAddress
正确;Address::PartyAdress
是正确的。Event::Address
需要工作。地址是一个识别参考表;如果使用,它将是父级,Event
将是子级。我将其留给您来识别/建模某个位置的多个事件
,以及一个或多个位置的事件
。可能涉及一个场地。或者一个
EventOccurrence
但是,如果它是在多个位置发生的通用
Event
,则不需要实体,则Address
是已在订单
中。U.3) 假设
Catalog
是传统意义上的条目 (JCPenney 2011),即待售或出租物品的列表。OrderSaleItem
正确临界点。
Catalog
是从属的,并且只能作为资产存在于Band
的上下文中。美好的。这意味着数据库中除 Band 商品外没有其他商品。正确吗?我可以看到“蓝调兄弟晚间表演”是一项可以订购、开具发票和付款的
活动
。还评论、评论等。我看不出
Song
是如何融入其中的。乐队销售专辑、歌曲还是两者兼而有之?还有没有其他乐队商品:音乐会/活动纪念品;海报;雕刻小眼镜?
与您引用的命名约定以及数据库的其余部分一致,
Catalog
(内容)应命名为Item
(行)。您已经(自然地?)在OrderSaleItem
中使用了它,(而不是OrderSaleCatalog
。)流派
没有问题
项目被分类按一对多流派
。我认为另外
流派对一对多项目进行分类
。关系是一对多的(当我们到达物理时,它将被解析为关联表)。U.5) 最喜欢的
Item::Favorite
的基数被反转。当您更正该问题后,Favorite
主题区域将需要进一步建模。同一对实体之间的循环关系或双路径是未解析模型的信号。一般来说,一个是正确的,另一个是多余的。 (也有例外,但这里没有;当发生这种情况时,动词短语会区分它们。)
Band::Favorite
x 或Item::Favorite
都是正确的,两者都不是。Item::Favorite
似乎是正确的,因为Band
已在Item
中识别
同样,一个
Favorite
> 乐队和商品的实体听起来并不可靠。单个Favorite
实体中的每个标识符都是一个Party
。当我们标准化时它会崩溃,不妨要求在这个阶段澄清标识符。它要么是一个具有某种形式的区分(FavoriteType
)的实体,用于标识其处理方式;或者一个最爱
用于乐队,另一个用于商品,在这种情况下不需要区分,消除了歧义。U.6) 业务规则
这可能是您唯一薄弱的领域。一般反应。您已经单独完成了这些任务(所有建模与编写 BR)。这些与型号不匹配。当您经历下一个周期时,以业务规则为指令,同时对它们进行调整,就像实体、关系和动词短语一样。
问题
Q.1) 用户/朋友
你完美地掌握了它的本质。以及关系的基数。 (对这一点进行全面处理。)对于 Accepted
Friend
来说这是正确的。因此时态应该是过去时(与大多数行一致)
Requested
和待处理的Accepted
是少数。通过IsAccepted
位或布尔值轻松实现。稍后您可能会遇到
IsRejected
或IsBlocked
(后者应该是一个单独的实体)。这是您所需要的吗?
Q.2)
Person 是零到多个用户
的基础是什么?小问题
M.1) 仅单数。
M.2)
参与方具有零到多个地址
。我认为他们必须拥有一个才能进行业务(但可能不适用于所有用户
)。M.3)
订单可能有零到多笔付款
。 “需要”意味着第一个付款
必须与订单
同时插入。M.4)
OrderSaleItem
应为OrderItem
x 或Order
应为OrderSale
。取决于您是否设想将来使用OrderPurchase
。主题区域示例
不熟悉关系数据库建模标准的读者可能会发现 IDEF1X 表示法很有用。
如前所述,我不提供完整的数据模型,仅提供指导。这只是一个选定主题领域的一个进展。它在任何方面都不“正确”或完整。
你的动词短语非常好。我已经提供了替代方案供您考虑,它们不是“正确”或“更好”。您需要选择他们或您自己的进度。我们的目标是在每种情况下提供最简洁、最准确的 VP。
没有任何迹象表明
Person
是正确的而User
是不正确的,这正在等待您的回答。但我必须在模型中使用一些东西;由于您已将它们建模为单独的,因此评估对位可能会很有趣。因此,继续推进模型,然后再次发布(只需编辑问题,保留标题段落,然后替换其余部分)。
V1.1 和响应
这当然是一个进步。
我已经以伪合法格式重新对项目进行了编号,包括章节标题,以便我们可以在整个过程中保留编号,并不断添加内容。事实上,它也确实缓解了 SO 编辑问题。
U.3) 是否需要对目录部分进行整个重新设计,或者仅需要重新设计与乐队之间存在的识别关系?
不需要。这是在这个级别工作的伟大之处,您在这里做出的决定将是数据在其上运行的铁轨(作为货运)或不运行的铁轨(因此需要替代运输和重型起重来导出,其形式为大量代码或额外数据仓库)。而且这里的决策成本很低(建模时间、论文)。
现在,项目仅存在于乐队的上下文中。它是依赖的。为了允许非乐队商品,它需要是独立的。然后现有的超/子类型集群需要重新设计。
尝试使用模组来销售完整的专辑或歌曲。无论哪种方式,它们都是电子格式,仅供下载。这就是为什么我将专辑列为由歌曲组成的原因
而不是 2 个独立的实体。
不确定您的意思(您有两个独立的实体)。
看来您还没有看到我的主题区域示例。 注意,如果您现在打开它,它包含我添加的 V1.1 的位;我没有改变昨天的内容,即 V1.0 响应。
实际上,这意味着您应该在查看示例时再次浏览我的 V1.0 答案。
U.5) ...但我不清楚如何做。我在这里缺少什么?
具有分化的一个实体的一个例子是您拥有的任何超类型/子类型集群。 The favorite 是超类型,BandFavourite 和 ItemFavourite 是子类型;允许每个分别引用 Band xor Item。
您已经对 ItemFavourite 进行了建模。现在的问题是,ItemFavourite 的事实是否意味着该 Band 是 Favourite?或者 BandFavourite 是一个离散的事实?在示例中,我对后者进行了建模,没有 Favourite::ItemFavourite/BandFavourite 结构。
Q.1) 是的,我希望接受、拒绝和阻止。我不确定您指的是这将如何改变逻辑模型?
V1.0 没有变化(我已经说过它非常完整),但您可能需要一个额外的实体。
您需要在 Friend 中使用三个位或布尔指示器。这将为这些状态提供服务:
已请求
(但未接受)已请求且未接受已接受
.
但被阻止的人不是朋友(或者以前可能是朋友,但自从被阻止后就不再是朋友)。因此,要么必须更改实体名称以反映这一点(两个关系无需更改),要么 Blocked 必须是一个单独的实体。第二个关系的两个不同含义会导致复杂性,因此我会选择后者。
对于前者,我们还有其他状态:
已阻止
。
。
Q.2)一个人不一定是用户。他们只能作为乐队成员而存在。这就是你要问的吗?
不。为什么我们需要区分 Person 和 User ?单独的操作或属性是什么?到目前为止,我将 Person 和 User 视为同一个实体; Person 是没有活动的用户。
这是最后一项,阻碍我们处理核心主题领域。
M.3) 我需要阅读更多关于约束检查的内容,以确保我理解事情。
M.4) 取决于您是否设想将来使用 OrderPurchase。您能详细解释一下您在这里的意思吗?
在模型的背景下。您提供用于制作(项目)销售订单的结构。因此,Item、Order 和 OrderItem。
但是,如果您还提供了跟踪采购订单的结构(购买物品以及办公用品、租金等),那么您需要区分销售订单和采购订单。因此:
项目
OrderSale 和 OrderSaleItem
OrderPurchase 和 OrderPurchaseItem
版本 1.1
U.2) 事件进展
EventDate 看起来不错。我将关系定义为
Event Was Perfromed On EvenDate
。虽然 ItemGenre 很完美,但 Event::Venue 需要改进。这是您一贯犯的错误,因此需要解释。
您已正确建模
Venue
,它是独立的并且确实存在于Event
的上下文之外。但是活动可能在零到多个[独立]场地[举行]
是不可能的。活动在许多场馆举行,而场馆也举办许多活动。如果仅此而已,由于这是逻辑级别,因此您可以绘制多对多关系,然后就完成了。在物理层面,该关系是通过实现关联表来解决的,其中的PK是两个父PK,并且没有数据。 (敌人就是一个很好的例子。)
但是如果有数据(例如,您需要跟踪参加者的日期或数量或其他内容),那么它就不是关联表,而是另一个实体。发生在活动和场地之间的事情。
EventDate 是一个不错的选择。我们已经有了那个和日期。只需添加场地并搅拌即可。我将在活动和场地之间发生的事情称为表演。
同样,EventAddress 已取得进展,但尚未完成。
活动有地址或场地有地址吗? (建模,无需言语)
如果地点:您是否需要该地点的所有历史地址(如派对),还是只需要当前地址(如订单)?
M.5) 子流派。你能解释一下为什么子流派是(a)独立的和(b)关系是非识别的。
M.6)
项目是零到多个收藏夹
。因此:项目是零到多个用户的最爱
。同样,每个用户选择零到多个收藏夹
。因此每个用户都会选择零到多个最喜欢的项目
。V1.2 和响应
巨大进步。
U.2) 事件
根据您的编辑和新要求进一步进展,有些是,有些不是。数据模型的所有其他主题领域都非常完整(对于逻辑),这一领域很混乱,几乎没有得到解决。部分是因为增加了要求(没有抱怨,这在现实生活中发生;这取决于你如何处理它)。
我在这里要强调的要点是,数据模型应该始终对现实世界进行建模,而不仅仅是业务需求。 (a) 使 DM 免受变更的影响,(b) 为添加的需求提供坚实的平台。这并不意味着您必须对整个现实世界进行建模,但是您建模的部分必须反映现实,而不是被压缩以满足需求。
其次,活动、乐队活动、表演等之间的区别缺乏明确性。现在,活动是派对-乐队-项目-活动。这很好,但它不适用于新样式的“按要求事件”。
第三,你对派对地址和秩序有很好的把握,但对场地却把握不好。
由于您接受符合标准的模型并因此接受处理,因此地址是一个参考表。
它是独立的(方角)
实际上,您可以将地址及其上方的所有内容放在第一页上;将模型的这部分设为两页,并且仅在该页上有地址。
正确建模:一方有地址历史。他们必须至少拥有一项当前的 { IsBilling |正在运送 | IsPhysical } 地址,基于正在执行的任何活动。
正确建模:一个订单有一个 IsBilling 地址(如果需要 IsShipping,则需要添加单独的关系)。
地址不是地点的子项(也是独立的,正确)。我不认为场地位于零到多个地址中。 (也许这是旧的基数反转错误,但我不确定,因为事件和地点的其他混乱。)
实际上地址::订单是可疑的。 (问题.3)您希望订单引用任何有效地址,还是执行订单方的特定地址?
返回活动。接受声明的 EventDate。这很好,但评论等适用于一般音乐会,而不是他们在蘑菇上表演的单一音乐会。
获取 V1.3。
您的术语“事件”等与要求等一致,但不支持所述要求。
因此,让我们开始按照现实世界中使用“事件”的方式来使用“事件”,并以这种方式对其进行建模。我们所说的“活动”,即派对乐队项目,实际上是一种表演。而且不是预定的通用活动,而是在特定地点举行的单个活动。
这要么就是您对 EventDate 的意思,要么 EventDate 解析为 Performance。
如果你不介意的话,我就不打一千字了,给你一张图。 主题区域示例 V1.2< /strong>
请注意,每个事件的多个频段已解决。
动词短语直接来自天堂。一个地址主办了多个场馆,每个场馆举办多个活动,每个场馆都有多个表演,每个场馆都是一个派对乐队项目。
U.3) 是时候将 Item 和 Band 之间的链接移至 Item 和 Party 了吗?根据目前的设计,我认为不可能销售与您提出的乐队无关的商品。
首先,我们需要使用关系术语,不是因为我是学究,而是因为真正的专家说这确实有助于过渡到关系世界。
其次,我们无法通过“移动关系”来实现这一点。
你必须对非乐队商品进行建模:你将如何销售它;追踪它;为此获得报酬。无论你想要评论和回复等。我不明白派对与它有什么关系,现在我们正在销售乐队物品,而不是派对物品。考虑引用完整性问题。
版本1.2
AR.1) 在完成FavoriteItem的练习后,我觉得要审核的Item需要多对多关系,因此需要指出。有必要吗?
在V1.1中,一个Item有很多Reviews,一个Review是关于一个Item的。一个人生成了许多评论(每个项目一个)。这是符合逻辑的。
评论涉及很多项目
是不合理的。如果有的话,现在 FavouriteItem/FavouriteBand 已经解决了,Review 也需要同样的解决和区分:我们是否需要区分 BandReview 和 ItemReview?好/坏的 ItemReview 是否表明好/坏的 BandReview 还是它们是离散的?
评论(就目前而言)不能是关于乐队或商品的。这意味着两个外键,其中之一将为 Null,并且不允许使用 Null FK。 Item和Band已经分化,而且分化已经成熟。
ItemReviews 可以进行总结等,但这是一个不同的故事。
U.7) 这给我们留下了一个需要解决的新问题。如果评论可以是关于乐队、专辑、歌曲或表演,我们如何确保引用完整性。我们不需要使用 AlbumReview 来引用 SongReview 等。对其进行建模。
R.5) 该模型当前在项目级别提供流派,这意味着专辑和歌曲(可以通过 CHECK 约束禁止商品)。不是乐队。鉴于(a)乐队会随着时间的流逝而变化,(b)在项目级别上进行分类更为精确,并且(c)乐队类型可以轻松从其专辑或歌曲中得出。
如果您需要单独的乐队类型,则需要添加。
事件类型呢?如果您需要,我认为每个事件将是一种流派。
请记住,诸如场地和流派之类的表是主要数据库中的严肃搜索标准。分析的向量。
数据仓库男孩需要 将其添加到维度中;在正确建模的数据库中,它们已经作为事实的维度存在。 向我展示所有吸引10,000多人的“民间音乐”活动的场所,这很容易。
.
讨论点。并不是说上述不正确。我在数据库和iTunes中发现的是精确计数。当您可以拥有类型的事情时,为什么Laissez Faire faire feare ::几件事。如果您只有类型:: Song,而Song只有一种类型,那么专辑和乐队都是精确的卷起。我们现在拥有它的方式,取决于数据输入人员的音乐知识,而genre ::的东西很多,所以它很松散。类型::歌曲很紧。
r.6)成员可以证明他们将参加事件没有建模。还阐明了兴趣与预订与出勤率。
R.8)未建模。
M.3)问题已经结束,但是动词短语保持不变。
M.7)逻辑模型相对于关联表。现在,该问题已关闭,请删除逻辑模型的任何关联表;任何剩余的表(两个父母之间)都包含数据。这意味着,浏览所有依赖表,并删除没有数据的所有。因此,v1.3应该少杂乱。
M.8)项目 IS OrderItem。
M.9)现在解决了党派 - 用户。独家亚型结构需要歧视,并且约束将用于执行完整性。有很多的地方,派对类型是必经之路。但是只有两个,列
ISBAND
或iSperson
就足够了。M.10)您已更正了基数反向的错误,但是某些动词短语仍在走错方向。
实际上, 1月27日
,我认为,如果我们进入逻辑密钥/属性级别(而不仅仅是实体关系级别),那么很多这些问题将更加清晰。现在是时候了。例如:
Q.3)订单:地址是可疑的。约束不是很正确,因为这将允许该订单具有任何任何地址,而不是针对执行订单的一方特定的地址。
但是,由于您是没有参考完整性的MySQL,因此您可能不知道它是如何在实际SQL中完成的,因此我将提供FK定义,这也是RI约束。期望您理解我的TERSE陈述是不公平的,而我的TERSE语句基于RM,当您没有SQL时由SQL进行标准化和支持。
order.partyid
),因此仅允许属于party的派对address的子集。a>
在第二部分中继续...
Method
I will cover specifics, but I will cover one or two Subject Areas completely, not all. You can pick that up and apply it to all subject Areas.
I have not responded to the core Subject Area, because we are still dealing with Identifying Entities. When that is resolved the
Reviews
, etc will be easier; the Transaction Entities are Dependent on the Identifying Entities.Direction
D.1) I know that I stated that I need to see the whole model. There is one exception. Historic or Temporal or Audit data (eg. the Edit and stored versions). At this early stage, they can be set aside; to be implemented just before completion of the Logical Model. This is in recognition that (a) they are simple Dependents of some parent (b) the parents need to be modelled in relation to all other tables first, and (c) to exclude unnecessary complications, and thus allow us to concentrate on the relevant field.
Has/Had
). Stay with present tense for now, because the focus is modelling, not archiving.Unresolved
U.1) Optional Parent
That is completely disallowed. Not just by IDEF1X, but by any notion of Integrity. If the FK Reference is defined, then there must be a Parent. To allow optional parents, the FK Reference must be removed (or not implemented). Such a condition would exclude the result from qualfying as a "Relational database", by definition. Eg.
Address:Order
.Order
must have anAddress
for legal or taxation reasons; that is separate to the Standard requirement issue..
U.2) Event
Party::PartyAddress
is correct;Address::PartyAdress
is correct.Event::Address
needs work. Address is an Identifying Reference table; if used, it would be the parent,Event
would be the child. I leave it to you to identify/model multipleEvents
to a location, andEvents
at one or multiple locations.There may be a Venue involved. Or a
EventOccurrence
But if it is a generic
Event
which happens at multiple locations, that does not need an Entity, theAddress
is already inOrder
.U.3) Assuming
Catalog
is an entry in the traditional sense (JCPenney 2011), a list of items for sale or hire.OrderSaleItem
is correctCritical point.
Catalog
is Dependent, and can exist only in the context of aBand
, as an Assset. Fine. That means no merchandise other than Band merchandise in the database. Correct ?I can see how "Evening performance with the Blues Brothers" is an
Event
that can be ordered, invoiced, and paid. Also reviewed, commented, etc.I can't see how
Song
fits into that. Are the bands selling albums, songs, or both ?Is there no other Band merchandise: concert/event souvenirs; poster; engraved shot glasses ?
Consistent with the naming conventions that you reference, and the rest of the database,
Catalog
(the cotent) should be namedItem
(the row). You have already (naturally ?) used that inOrderSaleItem
,( as opposed toOrderSaleCatalog
.U.4) Genre
No problem with
an Item is classified by one-to-many Genres
.I think additionally
a Genre classifies one-to-many Items
. The Relation is one-to-many (which will be resolved as an Associative table when we get to the Physical).U.5) Favorite
The Cardinality of
Item::Favorite
is reversed. When you correct that, theFavorite
Subject Area will require further modelling.Circular relation or dual paths between the same pair of Entities is a signal of an unresolved model. Generally one is correct and the other is redundant. (There are exceptions, but not here; and when this happens the Verb Phrases differentiate them.)
Either
Band::Favorite
xorItem::Favorite
is correct, not both.Item::Favorite
seems to be correct, becauseBand
is already identified inItem
Likewise, one
Favorite
Entity for bands and merchandise does not sound solid. Every Identifier in the singleFavorite
Entity is aParty
. It would break when we Normalise, might as well demand that the Identifiers be clarified at this stage. It is either one Entity with some form of differentiation (FavoriteType
) which identifies its treatment; or oneFavorite
for bands and another for merchandise, in which case differentiation is not required, ambiguity is eliminated.U.6) Business Rules
This is probably the only area you are weak in. General response. You have done the tasks separately (all the modelling vs writing BRs). These do not match the model. When you go through the next cycle, take the Business Rules as directives, and modulate them at the same time, as with the Entities, the Relations, and the Verb Phrases.
Question
Q.1) User/Friend
You have the essence of it perfectly. And the Cardinality of the Relations. (Full treatment on this one.) That is correct for Accepted
Friend
.therefore the tense should be past (go with the majority rows)
Requested
, and pendingAccepted
, are the minority. Easily implemented in aIsAccepted
Bit or Boolean.Later you may have
IsRejected
orIsBlocked
(that latter should be a separate Entity).Is that what you require ?
Q.2) What is the basis on which a
Person is zero-to-many Users
?Minor Issue
M.1) Singular only.
M.2)
Party Has zero-to-many Addresses
. I would think they must have one, in order to transact business (but perhaps not for allUsers
).M.3)
Order May Have zero-to-many Payments
. "Requires" means that firstPayment
has to be inserted at the same time asOrder
.M.4)
OrderSaleItem
shoulld beOrderItem
xorOrder
should beOrderSale
. Depends if you envisionOrderPurchase
in the future.Subject Area Example
Readers who are unfamiliar with the Standard for Modelling Relational Databases may find IDEF1X Notation useful.
As stated, I am not providing a finished Data Model, only guidance. This is just one progression of one selected Subject Area. It is not "right" or complete in any way.
Your Verb Phrases are excellent. I have provided alternatives for you to consider, they are not "right" or "better". You need to choose an progress them or your own. The goal being the most concise and accurate VP in each case.
No suggestion that
Person
is correct andUser
is incorrect, that is pending your answer. But I had to use something in the model; since you have modelled them as separate, a counterpoint may be interesting to evaluate.So go ahead and progress the model, then post again (just edit the question, leaving the header paras, and replacing the rest).
V1.1 and Response
That is certainly a progression.
I have re-numbered the items in pseudo-legal format, including the section headings, so that we can keep the numbering throughout, and keep adding to it. Actually it really eases the SO editing problems as well.
U.3) Would it require an entire rework of the Catalog section or just the identifying relationship that exists with the Band?
No. That's the great thing about working at this level, the decisions you make here will be the railroad tracks that the data runs on, as freight, or does not run on (and thus needs alternate transport and heavy lifting to derive, in the form of masses of code or an additional data warehouse). And the decisions here are cheap (modelling time, paper).
Right now an Item exists only in the context of a Band. It is Dependent. To allow non-band merchandise, it needs to be Independent. And then the existing super/subtype cluster needs rework.
Attempted a mod to sell both complete albums or song. Either way they would both be in electronic format only available for download. That is why I listed an Album as being comprised of Songs
rather then 2 separate entities.
Not sure what you mean (you have two separate entities).
It appears you have not seen my Subject Area Example. Note that if you open it now, it contains bits that I have added V1.1; I have not changed what was there yesterday, the V1.0 response.
Actually that means you should go through my V1.0 Answer again, while viewing the Example.
U.5) ... but how to is not clear to me. What am I missing here?
An example of one Entity with differentiation is any of the Supertype/Subtype clusters you have. The Favorite is the Supertype, BandFavourite and ItemFavourite are subtypes; allowing each to reference to Band xor Item respectively.
You have modelled ItemFavourite. Now the question is, does the fact of a ItemFavourite imply that the Band is Favourite; or is BandFavourite a discrete fact ? In the example, I have modelled the latter, without the Favourite::ItemFavourite/BandFavourite structure.
Q.1) Yes I would like to have Accepted, Rejected, and Blocked. I am not sure what you are referring to as to how this would change the logical model?
No change (I already stated it was pretty complete) to V1.0, but you might need an additional Entity.
You need three Bit or Boolean indicators in Friend. That will service these statuses:
Requested
(but not Accepted)Requested & Accepted
.
But Blocked is not a Friend (or could have been a Friend previously, but not since being Blocked). So either the Entity name has to change to reflect that (no change to the two Relations) xor Blocked has to be a separate Entity. Two separate meanings for the second Relation leads to complexity, therefore I would go with the latter.
With the former, we have additional statuses:
Blocked
.
.
Q.2) A person does not have to be a User. They can exist only as a BandMember. Is that what you are asking?
No. Why do we need to differentiate Person and User ? What are the separate actions or attributes ? Thus far, I see Person and User as the same Entity; Person is an User with no activity.
This is the last item, holding us back from dealing with the core Subject Area.
M.3) I need to read up more on Constraint Checking to make sure I am understanding things.
M.4) Depends if you envision OrderPurchase in the future. Can you expand as to what you mean here?
In the context of the Model. You provide the structures to make SalesOrders (of Items). Therefore Item, Order and OrderItem.
But if you provided the structures to track PurchaseOrders as well (to purchase Items as well as office supplies, rent, whatever), then you need to differentiate Sales Orders and Purchase Orders. Therefore:
Item
OrderSale and OrderSaleItem
OrderPurchase and OrderPurchaseItem
Version 1.1
U.2) Event Progressed
EventDate looks good. I would define the Relation as
Event Was Perfromed On EvenDate
.Whereas ItemGenre is perfect, Event::Venue Needs work. This is a mistake you make consistently, so an explanation is called for.
You have modelled
Venue
correctly, it is Independent and does exist outside the context ofEvent
. ButEvent May Be [Held] At zero-to-many [Independent] Venues
is not possible.Events are held at many Venues, and Venues host many Events. If that was all, since this is the Logical Level, you can draw a many-to-many Relation, and you are done. At the Physical level, that Relation is resolved by implementing an Associative Table, of which the PK is the two parent PKs, and there is no data. (Enemy is a good example.)
But if there is data (eg. you need to track the date or number of attendees or whatever), then it is not an Associative Table, it is another Entity. A Thing that Takes Place between Event and Venue.
EventDate is a good candidate. We already have that, and the date. Just add Venue and stir. I would call the Thing that Takes Place between Event and Venue a Performance.
Likewise, EventAddress has progressed but is not complete.
Do Events have Addresses or Venues have Addresses ? (model it, no need for words)
If Venue: do you need all the historic Addresses for the Venue (like Party), or just the current one (like Order) ?
M.5) SubGenre. Can you explain why SubGenre is (a) Independent and (b) the Relation is Non-Identifying.
M.6)
Item Is zero-to-many Favourites
. Therefore:Item Is a Favourite of zero-to-many Users
. Likewise,Each User Chooses zero-to-many Favourites
. ThereforeEach User Chooses zero-to-many Favourite Items
.V1.2 and Response
Great Progress.
U.2) Event Further Progressed
Going by your Edit as well as the new Requirements, some yes and some no. All the other Subject Areas of the Data Model are pretty much complete (for Logical), this one area is confused, not nearly as resolved. Partly because of the added Requirements (no complaint, that happens in real life; it is about how you handle it).
The main point I will make here is that the Data Model should always model the real world, as opposed to only the business Requirement. That (a) insulates the DM from the effect of change and (b) provides a solid platform for added Requirements. That does not mean you have to model the whole real world, but the parts of it that you do model must reflect reality and not be squished up to fill just the Requirement.
Second, there is lack of clarity about the distinctions between Event, Band-Event, Performance, etc. Right now an Event is a Party-Band-Item-Event. That's fine, but it does not work for the new style Event per Requirement.
Third, you have a good handle on Address re Party and Order, but not re Venue.
Since you are accepting the Standard-compliant model and therefore the treatment, Address is a Reference table.
It is Independent (square corners)
Actually, you can place Address and everything above it on page one; making this part of the model page two, and have Address only on this page.
Correctly modelled: A Party has a history of Addresses. They must have at least one current { IsBilling | IsShipping | IsPhysical } Address, based on whatever activity is being executed.
Correctly modelled: An Order has one IsBilling Address (if you need IsShipping, you need to add a separate Relation).
Address is not a child of Venue (also Independent, correct). I do not think a Venue is located in zero-to-many Addresses. (Maybe that is the old Cardinality-reversed bug, but I am not sure, due to the other confusion re Event and Venue.)
Actually Address::Order is suspicious. (Q.3) Do you want Order to reference any valid Address, or a specific address for the Party executing the Order ?
Back to Event. Accepting EventDate as declared. That's fine but then Reviews etc, apply to the generic concert and not the single concert which they performed on mushrooms.
Go for V1.3.
Your terminology re Event, etc is consistent with the Requirement, etc. but it does not support the Requirement as stated.
So let us start using "Event" the way it is used in the real world, and model it that way. What we have been calling "Event", the Party-Band-Item, is actually a Performance. And not a generic one that is scheduled, but a single one at a specific Venue.
That is either what you meant with EventDate, or EventDate resolves into Performance.
If you do not mind, I will avoid typing one thousand words, and give you a picture. Subject Area Example V1.2
Notice that the multiple Bands per Event is resolved.
And the Verb Phrases are straight from heaven. An Address hosted multiple Venues, each of which catered multiple Events, each of which is multiple Performances, each of which is one Party-Band-Item.
U.3) Is it time to move the link between Item and Band up to Item and Party instead? With the current design I don't see a possibility to sell merchandise not tied to the band as you have brought up.
First, we need to use Relational terminology, not because I am a pedant, but because the real gurus say it really helps to make the transition to the Relational world.
Second, we cannot accomplish that by "moving the Relation".
You have to model non-Band merchandise: how you are going to sell it; track it; get paid for it. Whether you want Reviews and Responses, etc. I do not see what Party has to do with it, and right now we are selling Band-Items, not Party-Items. Consider the Referential Integrity issues.
Version 1.2
AR.1) After going through the exercise for FavoriteItem, I feel that Item to Review requires a many-to-many relationship so that is indicated. Necessary?
In V1.1, An Item had many Reviews, and a Review was about one Item. A Person generated many Reviews (one per Item). That is logical.
A Review is about many Items
is not reasonable.If anything, now that FavouriteItem/FavouriteBand is resolved, Review needs likewise resolution and distinction: do we need to differentiate BandReview from ItemReview; does a good/bad ItemReview indicate a good/bad BandReview or are they discrete ?
a Review (as it stands) cannot be about either a Band or an Item. That means two Foreign Keys, and one of the will Null, and Null FKs are not allowed. Item and Band are alreay differentiated, and that differentiation is mature.
ItemReviews can be summarised, etc, but that is a different story.
U.7) That leaves us with a new issue to resolve. If a Review can be about a Band or Album or Song or Performance, how do we ensure that Referential Integrity. We do not need an AlbumReview to reference a SongReview, etc. Model it.
R.5) The model currently provides Genre at the Item level, that means Album and Song (Merchandise can be disallowed via a CHECK Constraint). Not Band. That may be enough, given that (a) bands change over time, (b) that kind of classification at the Item level is more precise, and (c) Band Genre can be easily derived from their Albums or Songs.
If you need separate Band Genres, you need to add that.
What about Event Genre ? If you need it, I think it will be one Genre per Event.
Keep in mind that tables like Venue and Genre are serious search criteria in a major database. Vectors for analysis.
The Data Warehouse boys need to add this in as Dimensions to their Facts; in a properly modelled Database, they already exist as Dimensions to Facts. Show me all the Venues with "Folk Music" Events scheduled that attracted more than 10,000 People is dead easy.
.
Discussion Point. Not saying the above is incorrect. What I have found in both Databases and iTunes is, precision counts. Why have laissez faire Genre::Several things when you can have Genre ::Specific Thing. If you had Genre::Song only, and Song has one Genre only, then Album and Band are precise roll-ups. The way we have it now, it depends on the music knowledge of the data entry person, and Genre::Thing is many, so it is loose. Genre::Song is tight.
R.6) members can show that they will be attending the Event is not modelled. Also clarify interest vs booking vs attendance.
R.8) Is not modelled.
M.3) The issue is closed, but the Verb Phrase remains unchanged.
M.7) Logical Model vis-a-vis Associative tables. Now that that issue is closed, remove any Associative tables for the Logical model; any remaining tables (between two parents) will contain data. That means, go through all the Dependent tables and remove any that do not have data. Thus V1.3 should be less cluttered.
M.8) Item is OrderItem.
M.9) Now that Party-Person-User is resolved. An Exclusive Subtype structure requires a Discriminator, and the Constrainst will be used to enforce Integrity. Where there are many, PartyType is the way to go. But for just two, a column
IsBand
orIsPerson
is adequate.M.10) You have corrected the cardinality-reversed bug, but some Verb Phrases are still going the wrong way.
27 Jan 11
Actually, I think a lot of these issues would be clearer if we move into the Logical Key/Attribute level (rather than just Entity Relation level). And it is high time we did. For example:
Q.3) Order:Address is suspicious. The constraint is not quite correct because that would allow the order to have any Address, not an Address that is specific to the Party executing the order.
But since you are MySQL, which has no Referential Integrity, you may not be aware of how it is done in real SQL, so I will provide the FK Definitions, which happen to be RI Constraints as well. It is kind of unfair to expect you to understand my terse statements, which are based in the RM, Normalisation and supported by SQL, when you do not have SQL.
Order.PartyId
), only the subset of PartyAddress which belongs to PartyId, will be allowed.Address Qualification Example
Continued in Part II ...