这个问题对我来说很难制定。如果需要澄清,请随时询问。
情况:我有一个使用Hibernate的Spring-Application在数据库中保存不同的Entity-Classes。为简化调用这些类E1, E2, .., E20
。所有这些类都基于相同的抽象@MappedSuperclass
,但没有真正的继承(在数据库方面)。
现在我想添加新的实体类(En1, En2, ...
)并与几个现有实体建立双向关系。假设En1
在E1,E2,E3
的实际情况中,我的代码如下所示:
@Entity
public class E1 extends SuperClass {
//other attributes
@OneToMany(mappedBy = "e1")
List<En1> newAttribut;
public En1 doMagic(En1 entity) {
//a long function which does somthing with the entity
}
//other attribute
}
//-----------------------------//
// The same code for E2 and E3 //
//-----------------------------//
@Entity
public class En1 {
//other attributes
@ManyToOne
E1 e1;
@ManyToOne
E2 e2;
@ManyToOne
E3 e3;
//other attributes
}
问题:此解决方案不能很好地扩展。我需要在每个关系的类En1
中有一个attribut,并且必须在每个现有实体中复制doMagic()
方法。此外,实际上,实体En1
一次只能与一个其他实体建立关系。因此,三个属性中有两个属于null
。
尝试过的解决方案:@Embeddable
的使用解决了E1,..,E3
public class EmbeddedEn1 implements Serializable {
@OneToMany(mappedBy="parentEntity")
private List<En1> newAttribut;
public En1 doMagic(En1 entity) {
//a long function which does somthing with the new entity
}
}
但无法建立"parentEntity"
双向。
继承不起作用:当然,我可以使用hasAttributEn1
继承的E1,E2,E3
类,但这不会与其他新的实体类一起扩展。假设以下情况,新实体En2,..,En4
应与以下实体相关:
En2 <-> E1, E3
En3 <-> E2,E3
En4 <-> E1,E2
在这种情况下,需要多重继承。
如何在不重复代码的情况下解决此问题的任何建议?
答案 0 :(得分:1)
我认为为了更好地解决您的模型,您可以使用hibernate inheritance。
+因此,对于实体En1
的情况,为E1,E2,E3...
创建父类:
@Entity
// TABLE_PER_CLASS will create a table for each subclass with all attributes
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
//....
//Abstract entity, so you won't need to create a table for it
public abstract class E extends SuperClass {
// shared attributes & methods
@OneToMany(mappedBy = "e")
private List<En> newAttribut;
public En doMagic(En entity) {
//a long function which does something with the new entity
}
//...
}
doMagic(En1)
删除newAttribute
和E1,E2,E3
,因为他们将从父类E
<强>更新强>:
正如您在评论中所提到的(以及您的问题),您需要将E
课程与多个En
课程相关联。
为简单起见,我还将En
用于hibernate继承:
@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public abstract class En{
@ManyToOne
private E e;
// ...
}
因此每个En1, En2,..., Enx
都将继承此类。
例如,如果您要保存En2 <-> E3
&amp; En3 <->E3
(此示例仅供参考,不包括交易等其他方面):
En en2 = new En2();
En en3 = new En3();
E e3 = new E3();
en2.setE(e3);
e3.getEn().add(en2);
en3.setE(e3);
e3.getEn().add(en3);
session.save(e3)
session.save(en2)
session.save(en3)
最后,您将满足您的约束条件:
doMagin()
方法的一个副本,
En
的子实体(例如:En1
)只与一个其他实体(例如:E1
或E3
)有关联一时间。
答案 1 :(得分:0)
您可能希望为E1,E2,...,E20定义泛型类型,这样您只需要使用单个E类型集合定义En类。 E的每个实现都可以不同,但您不需要更改En类,因为它只是包含E类型的集合。