精华内容
下载资源
问答
  • Hibernate实体关联关系映射

    千次阅读 2018-08-03 10:52:40
     简单来说Hibernate是ORM映射的持久层框架,全称是(Object Relational Mapping),即对象关系映射。  它将数据库中的表映射成对应的对象,以对象的形式展现,这样我们就可以通过映射的对象来对数据库中的数据...

    一、什么是Hibernate中的关联映射?

      简单来说Hibernate是ORM映射的持久层框架,全称是(Object Relational Mapping),即对象关系映射。

      它将数据库中的表映射成对应的对象,以对象的形式展现,这样我们就可以通过映射的对象来对数据库中的数据进行间接的操作。

      关联映射是将数据库中的表映射成与之相对应的对象,当你对这个对象进行操作的时候,Hibernate会对数据库中对应的表执行相应的操作,你对该实体的操作实际上就是在间接的操作数据库中与之相对应的表。

      Hibernate正是实现了这种思想,达到了方便开发人员以面向对象的思想来实现对数据库的操作。 

    二、Hibernate主要实现的映射关系:

            

     

    三、Hibernate映射的基本结构

        hibernate在实现ORM功能的时候主要用到的文件有:映射类(*.Java)、映射文件(*.hbm.xml)和数据库配置文件(*.properties/*.cfg.xml),它们各自的作用如下。

            映射类(*.java):它是描述数据库表的结构,表中的字段在类中被描述成属性,将来就可以实现把表中的记录映射成为该类的对象了。

            映射文件(*.hbm.xml):它是指定数据库表和映射类之间的关系,包括映射类和数据库表的对应关系、表字段和类属性类型的对应关系以及表字段和类属性名称的对应关系等。

            数据库配置文件(*.properties/*.cfg.xml):它是指定与数据库连接时需要的连接信息,比如连接哪种数据库、登录数据库的用户名、登录密码以及连接字符串等。当然还可以把映射类的地址映射信息放在这里。

     

    四、hibernate中的关联关系有四种:一对一、一对多、多对一、多对多。

     

    1、单向关联与双向关联

     单向关联:单向关联是指只有一方有另一方的关联信息而另一方没有关联信息                    

      

        A——>B  

        A对象中有B对象的关联信息

        B对象中没有A对象的关联信息

        我们可以通过A对象中B的关联信息查询或修改B对象的信息但无法通过B对象来查询修改A对象的信息

     双向关联:双向关联是指两方都有另一方的关联信息

      

        A<——>B

        A对象中有B对象的关联信息

        B对象中也有A对象的关联信息

        我们可以通过A对象中B的关联信息查询或修改B对象的信息也可以通过B对象来查询修改A对象的信息

     

    单向关联一般在一方配置多方不进行配置

      如:一对多 单向关联在“一”的一方配置文件里进行配置,"多"的一方不进行配置

    双向关联两方都要配置

      如:一对多 双向关联在“一”的一方配置文件里需要配置,“多”的一方也需要进行配置

     

    2、一对一关联映射

      一对一关联:一对一是指一个对象对应一个对象  如:一个人只有一个身份证。

      在两个数据表之间的一对一关系可以有两种实现方法,其中一种就是通过两个表的主键相关联,另一种是通过外键相关联

        如:一个人(Person)对应一个地址(Address)代码如下。

     (1)一对一主键单向关联: 

        Person——>Address

    public class Person {
        private int personid;
        private String name;
        private int age;
        //在Person对象中有Address对象的关联信息
        private Address address;
     
    public class Address{
        //Address对象中没有Person对象的关联信息
        private int addressid;
        private String addressdetail;

    这种单方面有另一个对象的关联信息的时候我们称为单向关联,再来看一下两个表中的映射hbm.xml文件:

    Person.hbm.xml

    <hibernate-mapping>
        <class name="com.entity.Person" table="PERSON">
            <id name="personid" column="presonid">
                <!--基于主键关联时,主键生成策略是foreign,表明根据关联类生成主键-->
                <generator class="foreign">
                    <!--关联持久化类的属性名-->
                    <param name="property">address</param>
                </generator>
            </id>
            <property name="name"/>
            <property name="age"/>
            <!--constrained设定为true,表示的主键必须与Person中对应资料的主键相同。-->
            <one-to-one name="address" constrained="true"/>
        </class>
    </hibernate-mapping>

    单向关联和双向关联的区别主要在于单向只在一方配置而双向两方都要配置

    Address.hbm.xml 

    因为是单方面关联所以只在Person.hbm.xml中配置了关联信息而Address.hbm.xml中不做任何配置

    所以我们省略Address.hbm.xml

      …………

     

    (2)一对一主键双向关联:

      Person<——>Address

    public class Person implements java.io.Serializable { 
    
      private Long id; 
      private String name; 
      //双向关联中Person对象中有Adderss对象的关联信息  
      private Address address;
     
    public class Address implements java.io.Serializable { 
      private Long id; 
      //Adderss对象中也有Person对象的关联信息  
      private Person person; 
      private String detail;

    这种两方面都有另一个对象的关联信息的时候我们称为双向关联,再来看一下两个表中的映射hbm.xml文件:

    Person.hbm.xml

    <hibernate-mapping> 
      <class name="entity.Person" table="person"> 
        <id name="id" type="java.lang.Long"> 
          <column name="id" /> 
          <generator class="identity" /> 
        </id> 
        <property name="name" type="java.lang.String"> 
          <column name="name" length="24" not-null="true"> 
            <comment>姓名</comment> 
          </column> 
        </property> 
        <one-to-one name="address"/> 
      </class> 
    </hibernate-mapping>

    单向关联和双向关联的区别主要在于单向只在一方配置而双向两方都要配置 

    Address.hbm.xml

    <hibernate-mapping> 
      <class name="entity.Address" table="address" catalog="mydb"> 
        <id name="id" type="java.lang.Long"> 
          <column name="id" /> 
          <!-- class="foreign": 一对一主键映射中,使用另外一个相关联的对象的标识符 --> 
          <generator class="foreign"> 
            <param name="property">person</param> 
          </generator> 
        </id> 
        <property name="detail" type="java.lang.String"> 
          <column name="detail" length="120" not-null="true"> 
            <comment>详细地址</comment> 
          </column> 
        </property> 
        <!-- 表示在address表存在一个外键约束,外键参考相关联的表person --> 
        <one-to-one name="person" constrained="true" /> 
      </class> 
    </hibernate-mapping>

     当我们操作Person对象时,可以对Address对象进行操作,也可以操作Address对象时对Person对象进行操作这样就形成了双向的关联

    双向关联还需要在hibernate.cfg.xml中进行配置

    <hibernate-configuration> 
    
      <session-factory> 
        <property name="connection.username">root</property> 
        <property name="connection.url"> 
          jdbc:mysql://localhost:3306/testdb 
        </property> 
        <property name="dialect"> 
          org.hibernate.dialect.MySQLDialect 
        </property> 
        <property name="connection.password">xiaohui</property> 
        <property name="connection.driver_class"> 
          com.mysql.jdbc.Driver 
        </property> 
        <property name="show_sql">true</property> 
        <property name="format_sql">true</property> 
    
       <!--在hibernate.cfg.xml中配置hbm.xml文件-->
        <mapping resource="com/entity/Person.hbm.xml" /> 
        <mapping resource="com/entity/Address.hbm.xml" /> 
    
      </session-factory> 
    
    </hibernate-configuration>

    (3)一对一外键单向关联:

      Person——>Address

    public class Person {
        private int personid;
        private String name;
        private int age;
        private Address address;
     
    public class Address{
        private int addressid;
        private String addressdetail;

    Address.hbm.xml

    
    <!--address中不做任何配置所以我们省略-->
    
      …………………………
    
    <!--单向关联和双向关联的区别在于单向关联只在一方配置双向关联两方都要配置-->
    Person.hbm.xml
    <hibernate-mapping> 
            <class name="com.entity.Person" table="PERSON"> 
                    <id name="personid"> 
                            <generator class="identity"/> 
                    </id> 
                    <property name="name"/> 
                    <property name="age"/> 
                    <!--用来映射关联PO column是Address在该表中的外键列名,增加unique变成唯一的--> 
                    <many-to-one name="address" unique="true"/> 
            </class> 
    </hibernate-mapping>

    关联和主键关联不同的地方是采用<many-to-one>标签来映射,一对一唯一外键关联映射其实是多对一的特例。<many-to-one>指定多的一端unique为true,这样就限制了多的一端的多重性为一,就是这样来映射的。

    (4)一对一外键双向关联:

      Person<——>Address

    public class Person implements java.io.Serializable { 
    
      private Long id; 
      private String name; 
      private Address address;
     
    public class Address implements java.io.Serializable { 
      private Long id; 
      private Person person; 
      private String detail;

    Person.hbm.xml 

    <hibernate-mapping> 
      <class name="com.entity.Person" table="person"> 
        <id name="personid" type="java.lang.Long"> 
          <column name="personid" /> 
          <generator class="identity" /> 
        </id> 
        <property name="name" type="java.lang.String"> 
          <column name="name" length="24" not-null="true"> 
            <comment>姓名</comment> 
          </column> 
        </property> 
      <!--双向关联配置-->
        <one-to-one name="address" /> 
      </class> 
    </hibernate-mapping>

    Address.hbm.xml

    <hibernate-mapping> 
      <class name="com.entity.Address" table="address" catalog="testdb"> 
        <id name="addressid" type="java.lang.Long"> 
          <column name="addressid" /> 
          <generator class="identity" /> 
        </id> 
        <property name="detail" type="java.lang.String"> 
          <column name="detail" length="120" not-null="true"> 
            <comment>详细地址</comment> 
          </column> 
        </property> 
        <many-to-one name="person" class="entity.Person" unique="true"> 
          <column name="personid"> 
            <comment>人的ID</comment> 
          </column> 
        </many-to-one> 
      </class> 
    </hibernate-mapping>

    单向关联和双向关联的区别主要在于单向只在一方配置而双向两方都要配置所以一对一双向关联比单向关联多了一个在Person.hbm.xml文件中配置<one-to-one name="address" /> 

     双向关联还需要在hibernate.cfg.xml中进行配置

    <hibernate-configuration> 
    
      <session-factory> 
        <property name="connection.username">root</property> 
        <property name="connection.url"> 
          jdbc:mysql://localhost:3306/testdb 
        </property> 
        <property name="dialect"> 
          org.hibernate.dialect.MySQLDialect 
        </property> 
        <property name="connection.password">xiaohui</property> 
        <property name="connection.driver_class"> 
          com.mysql.jdbc.Driver 
        </property> 
        <property name="show_sql">true</property> 
        <property name="format_sql">true</property> 
    
       <!--在hibernate.cfg.xml中配置hbm.xml文件-->
        <mapping resource="com/entity/Person.hbm.xml" /> 
        <mapping resource="com/entity/Address.hbm.xml" /> 
    
      </session-factory> 
    
    </hibernate-configuration>

     注意:因为一对一的主键关联映射扩展性不好,当我们的需要发生改变想要将其变为一对多的时候变无法操作了,所以我们遇到一对一关联的时候经常会采用唯一外键关联来解决问题,而很少使用一对一主键关联。

     

    3、一对多关联映射

      一对多关联:一对多是指一个对象对应多个对象 同样也分为单向关联和双向关联 如:一个教室可以有多个学生

    (1) 一对多单向关联:

       Classes——>Student

    public class Classes {  
        private int id;  
        private String name;     
        //Set支持延迟加载因为多个学生所以我们用Set集合关联  
        private Set students;  
    }  
    public class Student {  
        private int id;  
        private String name;      
    }  

    单向关联只需在一方配置hbm.xml文件Student不需要配置所以就省略了 

    Classes对象中使用了set属性,但是只是说明了延迟加载的属性,并没有为属性配置对应的对象,属性的对象是要在映射文件中来配置的,需要添加set标签,并在set标签中添加<one-to-many>标签,具体如下代码:

    Classes.hbm.xml

    <hibernate-mapping>  
        <class name="com.hibernate.Classes" table="t_classes">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
            <set name="students">  
                <key column="classesid"></key>  
                <one-to-many class="com.hibernate.Student"></one-to-many>  
            </set>  
        </class>  
    </hibernate-mapping>  

    因为Classes一方是一方对应的Student是多方 所以我们要用<set>来关联一方

    Student.hbm.xml不做任何改变

      省略………………

     

    (2)一对多双向关联:

        Classes<——>Student

    public class Classes {  
        private int id;  
        private String name;     
        //Set支持延迟加载  
        private Set<Student> students;  
    }  
    public class Student {  
        private int id;  
        private String name; 
        //添加class对象关联信息因为是一方所以我们用一个对象关联
        private Classes classes;     
    }  

    Classes.hbm.xml

      因为与单向一对多配置一样所以就省略了 可以参考上面单向一对多的代码

    Student.hbm.xml

    双向我们需要两方都要配置代码如下:

    <hibernate-mapping>  
        <class name="com.hibernate.Student" table="t_student">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
            <!-- 在多的一端Student中添加一行新的Classes列 ,并且列的名称要和Classes.hbm.xml的列明相同-->  
            <many-to-one name="classes" column="classesid"></many-to-one>  
        </class>  
    </hibernate-mapping>  

     因为Student一方是多方对应的Classes是一方 所以我们要用<many-to-one>来关联一方

    4、多对多关联映射

     多对多关联:多对多关联是指多个对象对应多个对象 如:老师可以有多个学生,学生也可以有多个老师

    (1)多对多单向关联:

       Teacher——>Student

    public class Teacher {
        private int id;
        private String name;
        private Set<Student> students = new HashSet<Student>();
    }
    
    public class Student {
        private int id;
        private String name;
        private String title;
    }

    Teacher.hbm.xml

    <hibernate-mapping>  
        <class name="com.hibernate.Teacher" table="t_teacher">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
         <!--生成一张新表存放两个关联对象的ID-->
            <set name="students" table="Teacher_Sutdent">  
           <!--将Teacher表的外键关联 注意不是对象的属性是表中的字段-->
                <key column="teacher_id"></key>  
           <!--将Student表的外键关联 注意不是对象的属性是表中的字段--> 
           <many-to-many class="com.hibernate.Student" column="student_id"></many-to-many> 
          </set> 
       </class> 
    </hibernate-mapping>

    文件中要使用<many-to-many>标签,并且在标签中添加上对应的列关系,因为你要让两个对象中都要清楚它们之间的映射是如何使用的,并且在生成的关系表中哪一列是对应的自己的外键,所以要在该标签中指明,另外在<set>标签中添加table属性会指明要生成新表,下面的示例中添加了t_user_role,所以会生成新的关联表。 

    Student.hbm.xml不做任何配置所以省略

      …………

    (2)多对多双向关联:

      Teacher<——>Student

    public class Teacher {
        private int id;
        private String name;
        private Set<Student> students = new HashSet<Student>();
    }
    
    public class Student {
        private int id;
        private String name;
        private String title;
        private Set<Teacher> teachers = new HashSet<Teacher>();
    }

    Teacher.hbm.xml同单向多对多一样故省略

      …………

    Student.hbm.xml

    <hibernate-mapping>  
        <class name="com.hibernate.Student" table="t_student">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
         <!--生成一张新表存放两个表的Id-->
            <set name="teachers" table="Teacher_Student">  
           <!--将Teacher表的外键关联 注意不是对象的属性是表中的字段-->
                <key column="student_id"></key>  
           <!--将Student表的外键关联 注意不是对象的属性是表中的字段--> 
           <many-to-many class="com.hibernate.Teacher" column="teacher_id"></many-to-many> 
          </set> 
       </class> 
    </hibernate-mapping>

     

    5、多对一关联

        对比一对一关联映射和多对一唯一外键关联映射,其实它们两个都是使用了<many-to-one>本质上都是外键约束,只不过一对一的是唯一映射,需要添加unique="true"的属性,其它的它们两个是相同的。

      多对一关联:多对一关联是指多个对象对应一个对象 如:多个员工对应一个部门

    (1)多对一单向关联:

    public class Department {  
        private int id;  
        private String name;  
    }  
    
    public class Employee {  
        private int id;  
        private String name;  
        private Department depart;//注意这里是以部门的对象来作为员工的属性的,这个思想很关键,是建立起部门和员工关联的关键  
          
    }  

    Department.hbm.xml不做任何配置故省略  

      …………    

    Employee.hbm.xml

    <hibernate-mapping package="com.suo.domain">  
          
        <class name="Employee">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
            <many-to-one name="depart"></many-to-one>  
            <!-- many-to-one指明了外键 ,会根据反射机制,找到要和Employee建立多对一关系的类,该列默认的是可以为空的-->  
        </class>  
          
    </hibernate-mapping>  

    (2)多对一双向关联:

    public class Department {  
        private int id;  
        private String name;
        private Set<Employee> emps;//用集合来存储员工     
    }  
    
    public class Employee {  
        private int id;  
        private String name;  
        private Department depart;//注意这里是以部门的对象来作为员工的属性的,这个思想很关键,是建立起部门和员工关联的关键  
          
    }  

    Departement .hbm.xml

    <hibernate-mapping package="com.suo.domain">  
          
        <class name="Department">  
            <id name="id">  
                <generator class="native"/>  
            </id>  
            <property name="name"/>  
              
            <set name="emps">  
                <key column="depart_id"/><!-- key指明了员工表中的外键-->  
                <one-to-many class="Employee"/><!-- one-to-many指明了和哪个类进行一对多的映射 -->  
            </set>  
            <!--   
                用set标签表示Department中的员工集合的属性,这个属性并没有映射到数据库中的部门表中,  
                即部门表中,并没有emps这样的一个列。  
             -->  
        </class>  
          
    </hibernate-mapping>  

    Employee.hbm.xml同单向关联配置相同故省略

      …………

     

    五、 级联操作 Cascade:

    1、简单的介绍

    cascade和inverse (Employee – Department)

    l  Casade用来说明当对主对象进行某种操作时是否对其关联的从对象也作类似的操作,常用的cascade:

             none,all,save-update,delete, lock,refresh,evict,replicate,persist,

             merge,delete-orphan(one-to-many)。

       一般对many-to-one,many-to-many不设置级联,

         在<one-to-one>和<one-to-many>中设置级联。

    l  inverse表“是否放弃维护关联关系”(在Java里两个对象产生关联时,对数据库表的影响),在one-to-many和many-to-many的集合定义中使用,inverse=”true”表示该对象不维护关联关系;

       该属性的值一般在使用有序集合时设置成false(注意hibernate的缺省值是false)。

             one-to-many维护关联关系就是更新外键。many-to-many维护关联关系就是在中间表增减记录。

             注: 配置成one-to-one的对象不维护关联关系

     

    2、属性的解析
    class元素的lazy属性设定为true,表示延迟加载,如果lazy设为false,则表示立即加载。以下对这二点进行说明。
         立即加载:表示Hibernate在从数据库中取得数据组装好一个对象(如学生1)后, 会立即再从数据库取得数据组装此对象所关联的对象(如学生证1)。
         延迟加载:表示Hibernate在从数据库中取得数据组装好一个对象(如学生1)后,不会立即再从数据库中取得数据组装此对象所关联的对象(如学生1),而是等到需要时,才会从数据库取得数据组装此关联对象。

     

    <one-to-one>元素的cascade属性表明操作是否从父对象级联到被关联的对象,

    它的取得可以是以下几种:


         none:在保存,删除或修改当前对象时,不对其附属对象(关联对象)进行级联操作。它是默认值。
         save-update:在保存,更新当前对象时,级联保存,更新附属对象(临时对象,游离对象)。
         delete:在删除当前对象时,级联删除附属对象。
         all:所有情况下均进行级联操作,即包含save-update和delete操作。
         delete-orphan:删除和当前对象解除关系的附属对象。


    <one-to-one>元素的fetch属性的可选值是join和select,默认是select。当fetch属性设定为join时,表示连接抓取(Join fetching):Hibernate通过在Select语句中使用outer join(外连接)来获得对象的关联实例或者关联集合。

      当fetch属性设定为select时,表示查询抓取(Select fetching):需要另外发送一条Select语句抓取当前对象的关联实体或集合。

    3、代码练习

    <set name="emps" cascade="save-update">
     <key column="depart_id"/>
      <one-to-many class="Employee"/>
    </set>

    <set name="students" table="taacher_student" inverse="true"><!-- table是用来指定中间表的属性 -->
    <key column="teacher_id"></key><!-- 查找教师id时,链接中间表表的teacher_id -->
    <many-to-many class="Student" column="student_id"></many-to-many>
    </set>

    六、总结:

    1、单向关联

      (1)、一对一主键关联:单向关联时我们需要在有关联信息一方的配置文件里加入<one-to-one  constrained="true">并且将constrained属性设置为true 表示的主键必须与这个对象中对应资料的主键相同

      (2)、一对一外键关联:单向关联时我们需要在有关联信息一方的配置文件里加入<many-to-one unique="true">并且将unique属性设置为true 表示这个主键是唯一的

      (3)、一对多单向关联:单向关联时我们需要在有关联信息一方的配置文件里加入<set>在<set>中加入<one-to-many/>

          <set>  

             <key column="关联的外键">

             <one-to-many/>

          </set>

      (4)、多对多单向关联:单向关联时我们需要在有关联信息一方的配置文件里加入<set>在<set 中生成一张新表用来存放两个表的外键table="">中加入<key column="当前表的外键ID"><many-to-many clasee="关联对象路径" column="关联对象表的Id">

          <set table="">

              <key column=""/>

              <many-to-many class="" column="">

          </set>

      (5)、多对一单向关联:单向关联时我们需要在有关联信息一方的配置文件里加入<many-to-one>

     

    2、双向关联

      (2)、一对一主键关联:在从表的一方加入<one-to-oneconstrained="true">还需要在主表加入<one-to-one>

      (2)、一对一外键关联:除了在从表中加入<many-to-one unique="true">也需要在主表加入<one-to-one>

      (3)、一对多双向关联:除了在一方中加入<set><one-to-many></set>还需要在多放加入<many-to-one>

      (4)、多对多双向关联:需要在两方都加入<set><many-to-many></set>  注:<set>中的table="表名"   表明两方的配置要一样

           <set name="关联对象的属性名" table="生成一张新表">

             <key column="当前对象数据库表的外键"/>

             <many-to-many class="关联对象的类路径" column="关联对象数据库表的外键">

           </set>

         (5)、多对一双向关联:要在多方中加入<many-to-one>还要在一方中加入<set>

                <set>

                   <key column="关联外键"/>

                   <one-to-many>

                </set>

    展开全文
  • 关系 在UML类图中,常见的有以下几种关系: 泛化(Generalization), 实现(Realization),关联(Association),聚合(Aggregation),组合(Composition),依赖(Dependency) 1. 泛化(Generalization) ...

    类的关系

    在UML类图中,常见的有以下几种关系: 泛化(Generalization), 实现(Realization),关联(Association),聚合(Aggregation),组合(Composition),依赖(Dependency)

    1. 泛化(Generalization)

    【泛化关系】:是一种继承关系,表示一般与特殊的关系,它指定了子类如何特化父类的所有特征和行为。例如:老虎是动物的一种,即有老虎的特性也有动物的共性。

    【箭头指向】:带三角箭头的实线,箭头指向父类
    在这里插入图片描述

    2. 实现(Realization)

    【实现关系】:是一种类与接口的关系,表示类是接口所有特征和行为的实现.

    【箭头指向】:带三角箭头的虚线,箭头指向接口
    在这里插入图片描述

    3. 关联(Association)

    【关联关系】:是一种拥有的关系,它使一个类知道另一个类的属性和方法;如:老师与学生,丈夫与妻子关联可以是双向的,也可以是单向的。双向的关联可以有两个箭头或者没有箭头,单向的关联有一个箭头。

    【代码体现】:成员变量

    【箭头及指向】:带普通箭头的实心线,指向被拥有者

    在这里插入图片描述

    上图中,老师与学生是双向关联,老师有多名学生,学生也可能有多名老师。但学生与某课程间的关系为单向关联,一名学生可能要上多门课程,课程是个抽象的东西他不拥有学生。

    下图为自身关联:
    在这里插入图片描述

    4. 聚合(Aggregation)

    【聚合关系】:是整体与部分的关系,且部分可以离开整体而单独存在。如车和轮胎是整体和部分的关系,轮胎离开车仍然可以存在。

    聚合关系是关联关系的一种,是强的关联关系;关联和聚合在语法上无法区分,必须考察具体的逻辑关系。

    【代码体现】:成员变量

    【箭头及指向】:带空心菱形的实心线,菱形指向整体
    在这里插入图片描述

    5. 组合(Composition)

    【组合关系】:是整体与部分的关系,但部分不能离开整体而单独存在。如公司和部门是整体和部分的关系,没有公司就不存在部门。

       组合关系是关联关系的一种,是比聚合关系还要强的关系,它要求普通的聚合关系中代表整体的对象负责代表部分的对象的生命周期。
    

    【代码体现】:成员变量

    【箭头及指向】:带实心菱形的实线,菱形指向整体

    l_643c4dad-7818-4224-a713-709f29369bcc

    6. 依赖(Dependency)

    【依赖关系】:是一种使用的关系,即一个类的实现需要另一个类的协助,所以要尽量不使用双向的互相依赖.

    【代码表现】:局部变量、方法的参数或者对静态方法的调用

    【箭头及指向】:带箭头的虚线,指向被使用者

    l_e6f112ca-93d1-4338-88a3-898c66f0e203

    各种关系的强弱顺序:

    泛化 = 实现 > 组合 > 聚合 > 关联 > 依赖

    展开全文
  • 在生产中,很多场景下之间都存在一定的联系,之间的关系包括:依赖、关联、聚合、组合、继承等 ,通过学习之间的关系有利提高面向对象编程的能力,为解决生产实际问题打下基础。 假设有两个A和B,...

    依赖关系

    在生产中,很多场景下类与类之间都存在一定的联系,类之间的关系包括:依赖、关联、聚合、组合、继承等 ,通过学习类之间的关系有利提高面向对象编程的能力,为解决生产实际问题打下基础。

    假设有两个类,类A和类B,类A的某个成员方法的参数有类B,说明类A使用了类B,类A依赖类B,依赖关系即uses-a关系,依赖关系除了被依赖方作为依赖方的方法参数,还可能作为依赖方的方法返回值存在,这些都是依赖关系的表现形式。如下图所示:
    在这里插入图片描述
    依赖关系的例子有很多,比如:LocalDateTime的now方法根据时区ID创建LocalDateTime,这里说明LocalDateTime依赖ZoneId。

    public static LocalDateTime now(ZoneId zone) {
        return now(Clock.system(zone));
    }
    

    在UML中依赖关系使用虚线箭头表示,依赖方指向被依赖方:
    在这里插入图片描述
    LocalDateTime依赖ZoneId的关系如下图所示:
    在这里插入图片描述
    UML是什么?引用百度百科,统一建模语言(Unified Modeling Language,UML)是一种为面向对象系统的产品进行说明、可视化和编制文档的一种标准语言,是非专利的第三代建模和规约语言。UML是面向对象设计的建模工具,独立于任何具体程序设计语言。

    关联关系

    关联关系是一种强依赖的关系,假设有两个类,类A和类B,类B作为类A的成员变量存在,类A也可为类B的成员变量存在,如果互为成员变量则为双向依赖,否则为单向依赖。
    在这里插入图片描述
    关联关系与依赖关系的区别在于,依赖关系是一种临时的关系,依赖关系主要体现在方法参数,当调用方法时才有关系,关联关系是一种长期的关系,主体现在成员变量,无论是否调用方法这种关系都存在。

    比如:ZonedDateTime与LocalDateTime关联,ZonedDateTime是带时区的日期时间,ZonedDateTime关联LocalDateTime。
    在这里插入图片描述
    在UML中双向关联关系一条实线表示,单向关联为单向实线箭头表示 。
    在这里插入图片描述
    ZonedDateTime关联LocalDateTime的关系图表示如下:
    在这里插入图片描述

    聚合关系

    聚合关系是一种has-a关系,假设有两个类,类A和类B,类A包含类B,类B是类A的成员变量,聚合关系和关联关系都体现在成员变量,它们的区别在于:关联关系双方是平级的,是个体和个体的关系,聚合关系双方不是平级的,是整体和部分的关系。

    比如:LocalDateTime类中包括LocalDate date和LocalTime time,这是一种聚合关系。
    在这里插入图片描述
    在UML中聚合关系用下边的符号表示 聚合关系:

    在这里插入图片描述
    菱形连接整体,实线连接部分。LocalDateTime类中包括LocalDate date和LocalTime time聚合关系如下图:
    在这里插入图片描述

    组合关系

    组合关系是一种强聚合的关系,组合关系与聚合关系的区别在于:聚合关系中部分离开整体仍可存活,组合关系中部分离开整体没有意义,比如:人由身体、四肢等部分组成 ,它们的关系为组合关系。

    在UML中组合关系使用下边的符号表示:
    在这里插入图片描述
    人与身体、四肢的关系表示如下:
    在这里插入图片描述
    类与类之间的关系还有继承关系、接口实现关系,课程后边会详细讲解。

    配套视频下载

    传智燕青Java基础精讲教程带你从零基础自学Java到大牛课程开放下载

    展开全文
  • Java之间的关联关系

    万次阅读 多人点赞 2012-05-19 20:43:07
    Java之间的关联关系 UML类图中的关系分为四种:泛化、依赖、关联、实现;关联关系又可以细化为聚合和组合。 一、泛化(Generalization) 泛化是父类和子类之间的关系,子类继承父类的所有结构和行为。在子类中...
     
    

    Java类之间的关联关系

    UML类图中的关系分为四种:泛化、依赖、关联、实现;关联关系又可以细化为聚合和组合。

    一、泛化(Generalization)

    泛化是父类和子类之间的关系,子类继承父类的所有结构和行为。在子类中可以增加新的结构和行为,也可以覆写父类的行为。

    一般用一个带空心箭头的实线表示泛化关系,UML图如下:

    泛化对应Java中继承关系,即子类继承父类中出private修饰外的所有东西(变量、方法等)。示例代码:

    public class Animal {

    }

    public class Tiger extends Animal {

    }

    Tiger继承Animal,因此Tiger与Animal之间是泛化(继承)关系。这个很好理解。

    二、依赖(Dependency)

    依赖关系是一种使用关系,特定事物的改变有可能会影响到使用该事物的事物,反之不成立。在你想显示一个事物使用另一个事物时使用。

    一般用一条指向被依赖事物的虚线表示,UML图如下:

    通常情况下,依赖关系体现在某个类的方法使用另一个类作为参数。代码示例:

    public class Screwdriver {    //螺丝刀,作为人类的工具,是用来被人类使用的

    }

    public class Person{

           public void screw(Screwdriver src){    //拧螺丝,需使用螺丝刀

    }

    }

    Person类的screw()方法在使用时就得传入一个Screwdriver类型的参数,这样Screwdriver的改变就会影响到Person,因此Person与Screwdriver之间就是依赖关系(Person依赖于Screwdriver)。

    三、关联(Association)

    是一种结构关系,说明一个事物的对象与另一个事物的对象相联系。给定有关联的两个类,可以从一个类的对象得到另一个类的对象。关联有两元关系和多元关系。两元关系是指一种一对一的关系,多元关系是一对多或多对一的关系。两个类之间的简单关联表示了两个同等地位类之间的结构关系。当你想要表示结构化关系时使用关联。(可以想想Hibernate的关联关系)

    一般用实线连接有关联的同一个类或不同的两个类。UML图如下:

    通常情况下,关联关系是通过类的成员变量来实现的。代码示例:

    public class Company {   //公司

    private Employee emp ;  //一个公司雇员,公司与雇员之间就是一种关联关系。

    }

    public class Employee{

    }

    雇员作为公司的属性,不同于上面的依赖。依赖的话,雇员的改变会影响公司,显然不是。在这里雇员仅仅作为公司的一个属性而存在。因此Employee与Company之间是关联关系。关联关系还可以细分为聚合和组合两种。

    3.1  聚合(Aggregation)

    聚合是一种特殊的关联。它描述了“has a”关系,表示整体对象拥有部分对象。

    关联关系和聚合关系来语法上是没办法区分的,从语义 上才能更好的区分两者的区别。聚合是较强的关联关系,强调的是整体与部分 之间的关系。例如,学校和学生的关系。聚合的整体和部分之间在生命周期上没有什么必然的联系,部分对象可以在整体对象创建之前创建,也可以在整体对象销毁之后销毁。

    一般用带一个空心菱形(整体的一端-学校)的实线表示。UML图如下:

    与关联关系一样,聚合关系也是通过类的成员变量来实现的。示例代码:

    public class Student{

    }

    public class School{  

           private List<Student> students ;  //学校与学生是聚合关系

    }

    学校是整体,而学生是部分。学校与学生都是可以独立存在的,之间没有什么必然的联系。因此学校与学生就是聚合关系。

    3.2  组合(Composition)

    组合是聚合的一种形式,它具有更强的拥有关系,强调整体与部分的生命周期是一致的,整体负责部分的生命周期的管理。生命周期一致指的是部分必须在组合创建的同时或者之后创建,在组合销毁之前或者同时销毁,部分的生命周期不会超出组合的生命周期。例如Windows的窗口和窗口上的菜单就是组合关系。如果整体被销毁,部分也必须跟着一起被销毁,如果所有者被复制,部分也必须一起被复制。

    一般用带实心菱形(整体的一端)的实线来表示。UML图如下:

    与关联关系一样,组合关系也是通过类的成员变量 来实现的。示例代码:

    public class Menu{

    }

    public class Window{

           private List<Menu> menus ;

    }

    菜单的存在前提是窗口的存在,两者之间存在很强的拥有关系。且窗口对菜单的生命周期负责,只有在窗口创建之后,菜单才能够创建,菜单必须在窗口销毁之前销毁。因此Window与Menu之间是组合关系。

    聚合和组合的区别在于:

    聚合关系是“has-a”关系,组合关系是“contains-a”关系;聚合关系表示整体与部分的关系比较弱,而组合比较强;聚合关系中代表部分事物的对象与代表聚合事物的对象的生存期无关,一旦删除了聚合对象不一定就删除了代表部分事物的对象。组合中一旦删除了组合对象,同时也就删除了代表部分事物的对象。

    另外有一个差别是组合中的一个对象在同一时刻只能属于一个组合对象,而聚合的一个部分对象可以被多个整体对象聚合,例如一个学生可以在多个学校就读,而一个菜单在同一时刻只能是某个窗口内的对象。

    四、实现(Realization)

    实现关系指定两个实体之间的一个合约。换言之,一个实体定义一个合约,而另一个实体保证履行该合约。对类来说,就是一个类实现了一个接口。

    一般用一条指向接口的虚线表示,UML图如下:

    实现对应Java中的实现接口(implements)。示例代码:

    public interface Person{

    }

    public class Student implements Person{

    }

    这个和泛化一样很好理解。

    五、总结

    类间关系有很多种,在大的类别上可以分为两种:纵向关系、横向关系。纵向关系就是继承关系,它的概念非常明确,也成为OO的三个重要特征之一,这里不过多的讨论。

    横向关系较为微妙,按照UML的建议大体上可以分为四种:

    依赖    (Dependency)

    关联    (Association)

    聚合    (Aggregation)

    组合    (Composition)

    关于关联,聚合,组合在实现上并没有显著区别,相区别他们只有通过判断关系双方之间的实际关系,如关系强弱、创建与销毁之间有无必要关联等。

    它们的强弱关系是没有异议的:依赖 < 关联 < 聚合 < 组合<泛化(继承)

    实现方式区别:

    (1)    依赖关系:关系对象出现在局部变量或者方法的参数里,或者关系类的静态方法被调用

    (2)    关联关系:关系对象出现在实例变量中

    (3)    聚合关系:关系对象出现在实例变量中

    (4)    合成关系:关系对象出现在实例变量中

    (5)    Generalization: extends

    (6)    实现: implements

    展开全文
  • UML定义的关系主要有六种:依赖、属、关联、实现、聚合和组合。这些关系的理解和使用是掌握和应用UML的关键,而也就是这几种关系,往往会让初学者迷惑。这里给出这六种主要UML关系的说明和类图描述,一看之下...
  • JAVA之间的全部关系简述+代码详解

    千次阅读 多人点赞 2018-07-18 09:23:03
    (2)has a包括了 组合,聚合,关联关系 (3)use a包括了 依赖关系 一、继承关系 继承指的是一个(称为子类、子接口)继承另外的一个(称为父类、父接口)的功能,并可以增加它自己的新功能的能力。在Java...
  • C/C++ 类关系

    2013-11-17 15:43:16
    C/C++类关系 说明了中的各种关系关联、聚合/组合、依赖、泛化(继承)
  • 谈谈之间的关联关系与依赖关系

    千次阅读 2016-08-03 10:28:30
    对于很多刚刚接触UML的童鞋,可能会对之间的关联与依赖关系不太理解,今天小菜就浅薄的讲一下。 这块的确是有点乱,不过小菜突然找到了一个比较好的切入点,拿出来分享一下。 接触过设计模式的读者,会经常...
  • [UML] 类图之间的关系 | 1.关联关系

    千次阅读 2020-07-01 11:56:59
    在UML类图中,用实线连接有关联关系的对象所对应的,在使用Java、C++和C#等编程语言实现关联关系时,通常将一个的对象作为另一个的成员变量 在使用类图表示关联关系时可以在关联线上标注角色名 1.1 双向关联 ...
  • UML中之间的几种关系   (2012-04-15 17:35:29) http://blog.sina.com.cn/s/blog_59ca2c2a01012ido.html 转载▼ 标签:  ...类关系 ...之间可能存在以下几种关系关联(association)、依赖(depe
  • UML——类关系

    千次阅读 2018-04-28 13:13:46
    类图显示了一组,接口,协作以及它们之间的关系。在UML中问题域要被逐步转化,通过来...2、关联关系类B是A的一个内部成员变量,则认为A和B存在关联关系。如:class A { public: B m_b; A (){ }}...
  • 关系关联,组合,聚合,依赖)

    万次阅读 多人点赞 2018-03-19 11:03:34
    关系关联,组合,聚合,依赖)
  • UML图关联关系

    千次阅读 2018-08-03 00:32:59
    UML图关联关系 关联关系共有四种,由弱至强依次是:依赖 &amp;amp;amp;lt;关联 &amp;amp;amp;lt; 聚合&amp;amp;amp;lt;组合 依赖 从代码层面上看,被依赖的B作为参数被A在某个方法中...
  • 之间的依赖、关联、聚合、组合关系

    万次阅读 多人点赞 2018-04-23 20:01:43
    一、继承关系 继承指的是一个(称为子类、子接口)继承另外的一个(称为父类、父接口)的功能,并可以增加它自己的新功能的能力。在Java中继承关系通过关键字extends明确标识,在设计时一般没有争议性。在UML...
  • 的几种关联模式的讲解

    万次阅读 2019-02-19 23:17:03
    一般来说有六种关联方式:单向关联,双向关联,自关联,多重性关联,聚合关系,组合关系。 1.单向关联一般是把B作为A的一个属性来实用,例如Company是一个,Employee是一个。然而Company将Employee...
  • UML类图中间的几种关系

    千次阅读 2016-10-27 10:57:55
    在UML类图中,常见的有以下几种关系: 泛化(Generalization), 实现(Realization),关联(Association),聚合(Aggregation),组合(Composition),依赖(Dependency)  1. 泛化(Generalization)  ...
  • 对象的关联关系

    千次阅读 2018-11-09 22:15:49
    对象之间最弱的一种关联方式,是临时性的关联。代码中一般指由局部变量、函数参数、返回值建立的对于其他对象的调用关系。 class A{ public B method(C c,D d){ E e = new E(); ... B b = new B(); .....
  • 关联关系和依赖关系

    千次阅读 多人点赞 2016-11-04 01:00:23
    1、 关联关系 A关联B的意思是,如果实例化一个A的对象,同时,会有一个B的对象被实例化。简言之,B作为A的属性存在。如下: [java] view plain copy   class A{   ...
  • Java中的组合、聚合和关联关系

    千次阅读 2019-09-09 11:37:03
    在本教程中,我们将重点介绍 Java 的三种关系类型,这些关系有时很容易混合:组合、聚合和关联。 2.组合 组成是一种"belong-to"的关系类型。这意味着其中一个对象是逻辑上较大的结构,其中包含另一个对象。 ...
  • n-n(多对多)的关联关系必须通过连接表实现。下面以商品种类和商品之间的关系,即一个商品种类下面可以有多种商品,一种商品又可以属于多个商品种类,分别介绍单向的n-n关联关系和双向的n-n关联关系。单向的n-n关联...
  • 关系前言继承实现组合聚合关联依赖 前言 类图是使用频率最高的UML图之一,主要用于描述系统中所包含的以及它们之间的相互关系,帮助开发人员理解系统,它是系统分析和设计阶段的重要产物,也是系统编码和测试的...
  • 对象之间的6种关联关系

    千次阅读 2019-12-06 16:50:59
    关联,实线箭头,描述一种比较固定的关系,例如,人与住址。 聚合,实线空心菱形箭头,描述一种整体和部分的关系,强调部分可脱离整体而存在,例如,学校和老师,老师可脱离学校而存在。 组合,实线实心菱形箭头,...
  • 1) (Class)封装了数据和行为,是面向对象的重要组成部分,它是具有相同属性、操作、关系的对象集合的总称。 2) 在系统中,每个具有一定的职责,职责指的是所担任的任务,即要完成什么样的功能,要承担什么...
  • UML类图之关联关系

    千次阅读 2017-05-13 00:32:00
    关联(Association)关系是之间最常用的一种关系,它是一种结构化关系,...在UML类图中,用实线连接有关联关系的对象所对应的。 通常将一个的对象作为另一个的成员变量。在使用类图表示关联关系时可以在...
  • 正在学习uml,在网上找了这篇文章学习之间的关系,虽然作者讲的已经很清楚,但...1.种类: Generalization(泛化),Dependency(依赖关系)、Association(关联关系)、Aggregation(聚合关系)、Composition(合成关系)。
  • 在领域模型中,之间最普遍的关系就是关联关系。在 UML 中,关联是有方向的。以 Customer 和 Order 为例:一个用户能发出多个订单, 而一个订单只能属于一个客户。从 Order 到 Customer 的关联是多对一关联; 而...
  • EA&UML日拱一卒-关联关联类

    千次阅读 2017-04-12 20:18:36
    举例说明什么是关联类,怎么用关联类
  • 之间的关系

    万次阅读 多人点赞 2018-06-28 17:21:10
    之间的6种关系一、UMLa) Unified Modeling Language (UML)又称统一建模语言或标准建模语言b) 它是一个支持模型化和软件系统开发的图形化语言,为软件开发的所有阶段提供模型化和可视化支持c) 它不仅统一了...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 551,975
精华内容 220,790
关键字:

类的关联关系