-
数据库的多对多
1.1 数据库中不能直接映射多对多
处理:创建一个桥接表(中间表),将一个多对多关系转换成两个一对多注1:数据库多表联接查询
永远就是二个表的联接查询
-- 书本类别表
create table t_hibernate_category
(
category_id int primary key auto_increment,
category_name varchar(50) not null
);
-- 书本表
create table t_hibernate_book
(
book_id int primary key auto_increment,
book_name varchar(50) not null,
price float not null
);
-- 桥接表
-- 定义三个列,其实只要两个列
-- 一个类别对应多本书,一本书对应多个类别
create table t_hibernate_book_category
(
bcid int primary key auto_increment,
bid int not null,
cid int not null,
foreign key(bid) references t_hibernate_book(book_id),
foreign key(cid) references t_hibernate_category(category_id)
);
hbm.xml配置
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<!--
table对应着实体类所对应的表
name指的是全类名
-->
<class table="t_hibernate_category" name="com.entity.category">
<!-- name指的是类属性
type指的是类属性类型
-->
<id name="categoryid" type="java.lang.Integer" column="category_id">
<generator class="increment"></generator>
</id>
<property name="categoryname" type="java.lang.String" column="category_name"></property>
<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.entity.Book"/>
</set>
</class>
</hibernate-mapping>
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<!--
查询一本书为例
-->
<class table="t_hibernate_book" name="com.entity.Book">
<!-- name指的是类属性
type指的是类属性类型
-->
<id name="bookid" type="java.lang.Integer" column="book_id">
<generator class="increment"></generator>
</id>
<property name="bookname" type="java.lang.String" column="book_name"></property>
<property name="price" type="java.lang.Float" column="price"></property>
<set table="t_hibernate_book_category" name="categorys" cascade="save-update" inverse="false">
<!-- one -->
<key column="bid"></key>
<!-- many -->
<many-to-many column="cid" class="com.entity.category"/>
</set>
</class>
</hibernate-mapping>
public Book get(Book book) {
Session session = SessionFactoryUtil.getSession();
Transaction transaction = session.beginTransaction();
Book b = session.get(Book.class, book.getBookid());
if(b!=null&&new Integer(1).equals(book.getInit())) {
Hibernate.initialize(b.getCategorys());
}
transaction.commit();
session.close();
return b;
}
public Integer save(Book book) {
Session session = SessionFactoryUtil.getSession();
Transaction transaction = session.beginTransaction();
Integer save = (Integer) session.save(book);
transaction.commit();
session.close();
return save;
}
以新增为案例,private Integer init=0;定义init属性是为了控制是否懒加载;
if(b!=null&&new Integer(1).equals(book.getInit())) {
Hibernate.initialize(b.getCategorys());
}
在xml中 inverse属性一定要是一true一false;true的那方是被掌控的一方
public void del(Book book) {
Session session = SessionFactoryUtil.getSession();
Transaction transaction = session.beginTransaction();
session.delete(book);
transaction.commit();
session.close();
}
删除的话中间表相关联的数据会一起删除
public void del(category c) {
Session session = SessionFactoryUtil.getSession();
Transaction transaction = session.beginTransaction();
category c2 = session.get(category.class, c.getCategoryid());
for(Book b:c2.getBooks()) {
b.getCategorys().remove(c2);
}
session.delete(c2);
transaction.commit();
session.close();
}
被掌控的一方删除一定要注意是由掌控它的一方移除它对应的数据再去删除他自己需要删除的数据