Hibernate4注解详解之多对多对象映射

来源:互联网 发布:js发送get请求参数 编辑:程序博客网 时间:2024/04/30 03:15

3.多对多(在多对多的使用上,建议使用表间关联方式,使用外键关联冗余数据较为严重)

       1.1多对多外键关联

         Test和SubTest的id为auto_increment

         Test.class

         @OneToMany(cascade=CascadeType.ALL,fetch=FetchType.EAGER)

         @JoinColumn(name="eee")

         public List<SubTest> subtests;

         @OneToMany(fetch=FetchType.EAGER,cascade=CascadeType.ALL)

         @JoinColumn(name="ddd") //默认不填JoinColumn会自动生成一个外键字段

         private List<Test> tests;

         多对多的外键关联在两者间都采用OnetoMany的标签注解,然后使用JoinColumn。

         1.2多对多表间关联

         Test和SubTest的id为auto_increment

         Test

         @ManyToMany(cascade=CascadeType.ALL,fetch=FetchType.EAGER)

         @JoinTable(name="dog",joinColumns = {@JoinColumn(name="abc")},  

                            inverseJoinColumns =@JoinColumn(name = "bcd"))

         public List<SubTest> subtests;

         SubTest

         @ManyToMany(fetch=FetchType.EAGER,cascade=CascadeType.ALL)

         @JoinTable(name="dog",joinColumns = {@JoinColumn(name="bcd")},  

         inverseJoinColumns = { @JoinColumn(name= "abc")} )

         private List<Test> tests;

       对于多对多的表间关联,我建议使用JoinTable的方式,因为mappedBy的情况只支持单方面的,只能对一方使用mappedby,这意味着在对一方进行save数据的时候,关联表不会进行insert操作。而JoinTable的情况则都能行得通。并且在生成关系表dog的时候,由于两方地位同等,bcd和abc字段均只有外键关联(如果是一对多的情况产生的关系表,会有多的一方即bcd字段设置成为主键,产生的后果自己去思考)。

 

         综合上述几种配置,当我们在考虑一对一的情况下应当使用主键关联一对多的情况在外键关联和表间关联都可做选择,如果使用外键关联,则对于Test对象添加的list数据,不应当重复add相同的SubTest对象,因为hibernate只会当做一条数据来进行插入,如果确实是Test所拥有的SubTest对象有相同的情况,应该先new再add。这是外键关联不好的地方,也因此,在SubTest表中会出现冗余的数据(多个相同对象包含的外键不同而已)。而如果使用表间关联,则list可对同一个SubTest对相进行重复添加,而在处理上不会再SubTest表上insert多条数据,只会在关系表上insert多条数据。然而在一对多的情况下建立表间关联,当我们使用JoinTable的时候,因为通常hibernate在建表时会要求有主键,因此在关系表上bcd字段(SubTest的外键约束字段)为主键,就无法产生相同的数据。这是一个问题。目前我还在测试当中。多对多的情况,我会建议使用表间关联,因为外键关联的冗余数据问题比较严重。(特殊情况可考虑外键关联)

0 0