繁体   English   中英

对于派生数据库结构,什么是好的设计?

[英]What is a good design for a derived database structure?

填写表格的输入是一个大文件,其中包含唯一的animalId,它们的名称,它们的动物类型以及其他一些特定于动物类型的值。

该数据库如下所示:

table animal:
- animalId(pk)
- name
- type(fk to animalType table)   

table dogs:         
- dogId(pk)         
- animalId(fk to animal)    
- hasCoat           
- etc...            

table fish:
- fishId(pk)
- animalId(fk to animal)
- animalId(fk to animal)
- dorsalFinCount
- etc...

我以这种方式设计了它,因为我的另一个来源给了我一个唯一的键(animalId,它标识了全世界的单个动物……就像一个uri),而且我不想拥有一个大的带有空值的单一数据库(例如, hasCoat和hasDorsalFin),也不必连续​​搜索两个类型特定的数据库。 此外,我可以轻松扩展此结构(具有属性hasWing,wingColor等的表鸟)

我的(Java)程序设计如下:

abstract class Animal
- animalId
- name
- type

class Dog extends DatabaseObject 
class Fish extends DatabaseObject 

abstract class DatabaseObject 
    private UUID id;
    public DatabaseObject(){this.uuid = UUID.randomUUID();}
    public UUID getId();

问题是,Dog和Fish类是Animals,但是每个数据库条目都需要具有UUID, 因为在animal表中将唯一的animalId用作PK。 此外,Dog and Fish还应该扩展Animal,因为它们需要这些数据字段...但是在Java中这是不可能的,因为它们已经扩展了抽象DatabaseObject类。

一个解决方案可能是,“狗和鱼”成为动物类的班级成员,但这似乎是一个不好的方法。

您将如何解决此问题?您的设计(数据库和程序结构)的优点是什么?

编辑:由于我的假设(...一个PK不能用作另一个表中的PK)是错误的,因此我可以将dogId和fishId更改为animalId。 此外,这种数据库设计被称为子类型化

不要重新发明轮子,使用ORM。 如果您可以使用Hibernate,则已经有了继承映射功能。

您的设计类似于称为“类表继承”的设计模式。 您可以在此处访问具有相同名称的标签,也可以通过在网络上搜索来查看Martin Fowler对相同主题的处理方式。

我会为您建议一个小改动。 在您的情况下,它可能有效也可能无效。 它称为“共享主键”。 您摆脱了DogId和FishId。 而是将AminalID设置为狗和鱼表以及动物表的PK。 请注意,AnimalID将同时是PK和FK。 而且,您当然必须使其成为Animal中PK的真实副本。

这具有几个优点,其中包括简单性和速度。 但是最大的好处是,它强制了每个子类和超类之间IS-A关系的一对一性质。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM