多对多
多对多其实也分单向多对多,和双向多对多,但是单向多对多比较简单,并且用的最多的就是双向多对多了,知道了双向多对多,单向多对多就非常简单,所以我们直接讲双向多对多
生活中有很多例子就是双向多对多的,最简单和贴近我们生活的,
1、学生和选课之间的关系了,学生可以选择多门课程,课程可以被多个学生选择,
2、学生和选老师之间的关系,学生可以选择多个老师,老师可以有许多学生,
3、在淘宝中购物,一件商品能被多个人选择,一个人能够选择多个商品
4、....
很多这种多对多关系,就拿学生和老师这个例子来讲解吧
要保存多对多的关系,两张表是不够的,需要增加第三张表来表示这种关系,来看下面的数据库关系图。
这个图意思就是用t_s这个中间表来保存student和teacher这两张表的关系,并且t_s是联合主键,同时也是外键,指向student的id和teacher的id
有人肯定会觉得为什么还要用第三张表,不直接使用两个外键,你指向我,我指向你这样呢,这样会暴露出一个很大的问题,如果学过数据库就应该会知道,这样的两张表相互关联,那么这两张表的关系就固定在那里了,删哪个表就不能删,这个都市小事,当你在查询一个表中数据时,会造成死循环,你查了我,我又在查你,一直重复下去。
实体类和映射配置
Student持久化类和Student.hbm.xml
//Student实体类
private int id;
private String sname;
//维护了一个一方的对象
private Set<Teacher> teachers = new HashSet<Teacher>();;
//get方法和set方法
<hibernate-mapping package="com.java.pojo"> <class name="com.java.pojo.Student" table="student"> <id name="id" column="id"> <generator class="native"></generator> </id> <property name="sname" column="sname"></property>
<!--要查询到所有的teacher,就需要通过连接表,所以申明连接表的名称--> <set name="teachers" table="tea_stu">
<!-- 本实体类在连接表中的外键名称,让hibernate知道连接表中有一个外键名为sid的指向本实体类 --> <key column="sid"></key>
<!-- 多对多映射关系,映射类和其映射类在连接表中的外键名称 这个的意思跟上面的一样,也是声明让hibernate知道,这样一来,hibernate就知道如何查询了--> <many-to-many class="com.java.pojo.Teacher" column="tid"></many-to-many> </set> </class> </hibernate-mapping>
Teacher和teacher.hbm.xml
private int id; private String tname; //维护一个多方的集合,集合在这里需要初始化 private Set<Student> students = new HashSet<Student>();
//get方法和set方法
<class name="com.java.pojo.Student" table="student"> <id name="id" column="id"> <generator class="native"></generator> </id> <property name="sname" column="sname"></property> <!--要查询到所有的teacher,就需要通过连接表,所以申明连接表的名称--> <set name="teachers" table="tea_stu"> <!-- 本实体类在连接表中的外键名称,让hibernate知道连接表中有一个外键名为sid的指向本实体类 --> <key column="sid"></key> <!-- 多对多映射关系,映射类和其映射类在连接表中的外键名称 这个的意思跟上面的一样,也是声明让hibernate知道,这样一来,hibernate就知道如何查询了--> <many-to-many class="com.java.pojo.Teacher" column="tid"></many-to-many> </set> </class>
测试
public class Test { public static void main(String[] args) { Configuration configuration = new Configuration(); SessionFactory sessionFactory = configuration.configure().buildSessionFactory(); Session session = sessionFactory.openSession(); Transaction transaction = session.beginTransaction(); Student student = new Student(); student.setSname("Amy"); Teacher teacher = new Teacher(); teacher.setTname("王老师"); teacher.getStudents().add(student); session.save(teacher); session.getTransaction(); transaction.commit(); session.close(); sessionFactory.close(); } }
结果