6.关系映射(使用注解的方式表示)

写在前面

  这里的关系是指:对象之间的关系,并不是数据库的关系

  如:关系有单向和双向之分,但是在数据库中,单向关系和双向关系其实并没有什么区别,

    这里的单双向指的是对象之间是否能够相互访问

铁律: 1、凡是双向关联,必设mappedBy

    因为根本都没必要在2个表中都存在一个外键关联,在数据库中只要定义一遍就可以了

    mappedBy的意思就是“被映射”,即mappedBy这方不用管关联关系(即不生成外键字段),关联关系交给另一方处理
     2、双向关系在程序中要设定双向关联

存在以下关联关系

  1.一对一

    有两种策略可以实现一对一的关联映射:

    1.主键关联:即让两个对象具有相同的主键值,以表明它们之间的一一对应的关系;

    数据库表不会有额外的字段来维护它们之间的关系,仅通过表的主键来关联

    2.唯一外键关联:外键关联,本来是用于多对一的配置,

    但是如果加上唯一的限制之后,也可以用来表示一对一关联关系

  唯一外键关联(单向)

    @OneToOne 写在被引用对象的实体类中

    @JoinColum 为数据库表中这个外键指定个字段名称

 1 @Entity
 2 public class Husband {
 3     private int id;
 4     private String name;
 5     private Wife wife;
 6     
 7     @OneToOne
 8     @JoinColumn(name="wifeID")
 9     public Wife getWife() {
10         return wife;
11     }
12     public void setWife(Wife wife) {
13         this.wife = wife;
14     }
15     @Id
16     @GeneratedValue(strategy=GenerationType.AUTO)
17     public int getId() {
18         return id;
19     }
20     public void setId(int id) {
21         this.id = id;
22     }
23     public String getName() {
24         return name;
25     }
26     public void setName(String name) {
27         this.name = name;
28     }
29 }

  唯一外键关联(双向)

  mappedBy作用

  是指定这个一对一关联是被Husband类的 wife属性(准确说是getWife方法)做的映射

  Wife这边不生成外键字段,而是交给 Husband去生成外键字段

 1 @Entity
 2 public class Wife {
 3     private int id;
 4     private String name;
 5     private Husband husband;
 6     @OneToOne(mappedBy="wife")
 7     public Husband getHusband() {
 8         return husband;
 9     }
10     public void setHusband(Husband husband) {
11         this.husband = husband;
12     }

  主键关联(单向)

     @PrimaryKeyJoinColumn

  主键关联(双向)

      mappedBy

  

  联合主键关联(参考的那张表的主键不唯一时 会使用到) 

    @JoinColumns 

    注解联合主键一对一联系,然后再使用@JoinColumn 来注解当前表中的外键字段名,

    并指定关联哪个字段,使用referencedColumnName指定哪个字段的名称

 1 @OneToOne
 2     @JoinColumns(
 3             {
 4                 @JoinColumn(name="wifeId", referencedColumnName="id"),
 5                 @JoinColumn(name="wifeName", referencedColumnName="name")
 6             }
 7     )
 8     public Wife getWife() {
 9         return wife;
10     }

    

  

  2.多对一

    @ManyToOne

  3.一对多

    @OneToMany

  4.多对多

    @ManyToMany

  

 1 @ManyToMany
 2     @JoinTable(name="t_s",
 3     joinColumns={@JoinColumn(name="teacher_id")},  //会自动参考teahcer的 ID
 4     inverseJoinColumns={@JoinColumn(name="student_id")}  //会自动参考student的 ID
 5     )
 6     public Set<Student> getStudents() {
 7         return students;
 8     }
 9     public void setStudents(Set<Student> students) {
10         this.students = students;
11     }

注:关联关系中的CRUD_Cascade_Fetch

@OneToMany
(mappedBy="group",
cascade={CascadeType.ALL},fetch=FetchType.EAGER
)

1.设定cascade 可以设定在持久化时对于关联关系对象的操作(级联更新)(CUD ,R归Fetch管)

2.cascade仅仅是帮助我们省了编程的麻烦而已,不要把它的作用看的太大

3.fetch(FetchType.EAGER,(会被关联自动查询出来)FetchType.Lazy(不会自动关联查询出来,用到的时候才会去查询))

  如老师里面有 学生集合,当老师被查询时,这个老师的学生集合被直接加载出来,不管是否学生有没有用到   EAGER

  学生集合不会被直接加载,而是等到需要用到学生的时候,才会去加载学生集合   Lazy

  a) 铁律:双向不要两边设置Eager  (会有多余的查询语句发出)

  b) 对多方设置fetch的时候要谨慎,结合具体应用,一般用Lazy 不用 eager,

   特殊情况(多方数量不多的可以考虑,提高效率时可以考虑)

4.如果想消除关联关系,先设定关系为null,再删除对应记录(如果不设定为null,就会级联删除),

 如果不删除记录,该记录就变成垃圾数据

  5.集合映射

    1.Set

    2.List

      a) @OrderBy("name ASC")  

      //使用 @OrderBy注解List中使用哪个字段进行排序,可以组合排序,中间使用逗号分开

    3.Map  

      a) @MapKey(name="id")   //注解使用哪个字段为key

  6.继承关系(不重要)

    使用@Inheritance 注解为继承映射,再使用strategy属性来指定继承映射的方式

    strategy有三个值:InheritanceType.SINGLE_TABLE      单表继承

               InheritanceType.TABLE_PER_CLASS   类表继承

               InheritanceType.JOINED            具体表继承

a)单表继承            SINGLE_TABLE 
    把所有的属性都存储到一个表中,另外需要加入一个标识字段(表示哪个具体的子类)
    使用@DiscriminatorColumn   标识字段的字段名,及字段类型
    使用@DiscriminatorValue      来注解标识字段的值
    
b)类表继承   TABLE_PER_CLASS
    每个具体类 映射成一个表  ,子类之间的ID不能重复
    @TableGenerator来申明一个表主键生成策略
    @GeneratedValue(generator="t_gen", strategy=GenerationType.TABLE)来注解生成策略为表生成策略,并且指定表生成策略的名称

 c)具体表继承   JOINED
    每个类 映射成一个表  父类中包含了子类公共的一些字段,父类中一个ID对应一个子类
    只需要设置@Inheritance(strategy=InheritanceType.JOINED)

  7.组件映射(值对象 和 实体对象)

  @Embeddable

  @Embedded //用于注解组件映射,表示嵌入对象的映射

1 @Embedded
2     public Wife getWife() {
3         return wife;
4     }
5     public void setWife(Wife wife) {
6         this.wife = wife;
7     }

  /*Wife成了Husband的一部分,Wife中的这些字段,也会放到Husband中,Wife在这里只是一个对象,不需要任何注解*/

原文地址:https://www.cnblogs.com/xuzekun/p/7388798.html