1. 数据库的多对多关系:
1.数据库中不能直接映射多对多
处理:创建一个中间表,将一个多对多关系转换为两个一对多的关系
(hibernate可以直接映射多对多的关联关系)
2.Demo(书籍与书籍类别的关系)
一本书可以对应多个类别,同样一个类别也可以对应多本书(demo有张中间表,存放了书籍与类别的关系)
2.1Book类的实体映射文件
<!-- bid 为书籍id cid为书籍类别id -->(一本书对应多个类别)
<set table="t_hibernate_book_category" name="categories" cascade="save-update" inverse="false">
<!-- one -->
<key column="bid"></key>
<!-- many -->
<many-to-many column="cid" class="com.zking.five.entity.Category"></many-to-many>
</set>
2.2Category类的实体映射文件
public Integer add(Book book) {
Session session = SessionFactoryUtils.getSession();
Transaction transaction = session.beginTransaction();
Integer bid = (Integer)session.save(book);
transaction.commit();
session.close();
return bid;
}
一个书籍类别对应多本书
<set table="t_hibernate_book_category" name="books" cascade="save-update" inverse="true">
<!-- one -->
<key column="cid"></key>
<!-- many -->
<many-to-many column="bid" class="com.zking.five.entity.Book"></many-to-many>
</set>
3.多对多之增加
public Integer add(Book book) {
Session session = SessionFactoryUtils.getSession();
Transaction transaction = session.beginTransaction();
Integer bid = (Integer)session.save(book);
transaction.commit();
session.close();
return bid;
}
@Test
public void testAdd1() {
Book book = new Book();
book.setBookName("这个杀手不太冷");
book.setPrice(23f);
Category category = new Category();
category.setCategoryId(5);
book.getCategories().add(this.CategoryDao.get(category));
this.bookDao.add(book);
}
4.多对多之删除
public void del(Book book) {
Session session = SessionFactoryUtils.getSession();
Transaction transaction = session.beginTransaction();
session.delete(book);
transaction.commit();
session.close();
}
//主控方删除
在删除id为5的这本书时,能直接删除中间表的数据
@Test
public void testDel() {
Book book = new Book();
book.setBookId(5);
this.bookDao.del(book);
}
//被控方删除 无法删除
public void testDel2() {
Category category = new Category();
category.setCategoryId(5);
this.CategoryDao.del(category);
}
5. 多对多关系注意事项
- 一定要定义一个主控方
- 多对多删除
-
主控方直接删除
2. 被控方先通过主控方解除多对多关系,再删除被控方
3.禁用级联删除
-
- 关联关系编辑,不需要直接操作桥接表,hibernate的主控方会自动维护