1.Employee
package cn.itcast.b_one2Many;
public class Employee {
private int empId;
private String empName;
private double salary;
//员工与部门(多对一)
private Dept dept;
public int getEmpId() {
return empId;
}
public void setEmpId(int empId) {
this.empId = empId;
}
public String getEmpName() {
return empName;
}
public void setEmpName(String empName) {
this.empName = empName;
}
public double getSalary() {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
public Dept getDept() {
return dept;
}
public void setDept(Dept dept) {
this.dept = dept;
}
}
2.Dept
package cn.itcast.b_one2Many;
import java.util.HashSet;
import java.util.Set;
public class Dept {
private int deptId;
private String deptName;
//部门对应的多个员工(一对多)
private Set<Employee> emps=new HashSet<Employee>();
public int getDeptId() {
return deptId;
}
public void setDeptId(int deptId) {
this.deptId = deptId;
}
public String getDeptName() {
return deptName;
}
public void setDeptName(String deptName) {
this.deptName = deptName;
}
public Set<Employee> getEmps() {
return emps;
}
public void setEmps(Set<Employee> emps) {
this.emps = emps;
}
}
3.Employee.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<!--
This mapping demonstrates content-based discrimination for the
table-per-hierarchy mapping strategy, using a formula
discriminator.
-->
<!--映射文件:映射一个实体类对象,描述一个对象最终可以直接保存对象数据到数据库中 -->
<!-- package:要映射的对象所在的包(可选,如果不指定,此文件下所有的类都要指定全路径)
auto-import 默认为true,在写HQL的时候自动导入包名
如果指定为false,在写HQL的时候必须要写上类的全名-->
<hibernate-mapping package="cn.itcast.b_one2Many">
<class name="Employee" table="t_employee">
<id name="empId">
<generator class="native"></generator>
</id>
<property name="empName" length="20"></property>
<property name="salary" type="double"></property>
<!--多对一的映射
Employee映射关键点:
1.映射的部门属性:dept
2.映射的部门对象:对应的外键字段:dept_id
3.部门的类型-->
<many-to-one name="dept" column="dept_Id" class="Dept"></many-to-one>
</class>
</hibernate-mapping>
4.Dept.hbm.xml
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<!--
This mapping demonstrates content-based discrimination for the
table-per-hierarchy mapping strategy, using a formula
discriminator.
-->
<!--映射文件:映射一个实体类对象,描述一个对象最终可以直接保存对象数据到数据库中 -->
<!-- package:要映射的对象所在的包(可选,如果不指定,此文件下所有的类都要指定全路径)
auto-import 默认为true,在写HQL的时候自动导入包名
如果指定为false,在写HQL的时候必须要写上类的全名-->
<hibernate-mapping package="cn.itcast.b_one2Many">
<class name="Dept" table="t_dept">
<id name="deptId">
<generator class="native"></generator>
</id>
<property name="deptName" length="20"></property>
<!-- 一对多关联映射配置(通过部门管理到员工)
Dept映射关键点:
1.指定映射的集合属性:emps
2.集合属性对应的集合表:t_employee
3.集合表的外键字段:t_employee.dept_id
4.集合元素的类型-->
<set name="emps" table="t_employee">
<key column="dept_Id"></key>
<one-to-many class="Employee"></one-to-many>
</set>
</class>
</hibernate-mapping>
5.测试类
package cn.itcast.b_one2Many;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.hibernate.classic.Session;
import org.junit.Test;
public class App_save {
private static SessionFactory sf;
static{
sf=new Configuration()
.configure()
.addClass(Dept.class)
.addClass(Employee.class) //测试的时候使用
.buildSessionFactory();
}
//保存,通过部门方保存数据(一对多操作保存数据)
@Test
public void Save() {
Session session=sf.openSession();
session.beginTransaction();
//部门对象
Dept dept=new Dept();
dept.setDeptName("应用开发部");
//员工对象
Employee emp_zs=new Employee();
emp_zs.setEmpName("张三");
Employee emp_ls=new Employee();
emp_ls.setEmpName("李四");
//处理关系
dept.getEmps().add(emp_zs);
dept.getEmps().add(emp_ls);
//保存数据
session.save(emp_zs);
session.save(emp_ls);
session.save(dept);
session.getTransaction().commit();
session.close();
/* Hibernate: insert into t_employee (empName, salary, dept_Id) values (?, ?, ?)
Hibernate: insert into t_employee (empName, salary, dept_Id) values (?, ?, ?)
Hibernate: insert into t_dept (deptName) values (?)
Hibernate: update t_employee set dept_Id=? where empId=? //维护员工部门引用的id
Hibernate: update t_employee set dept_Id=? where empId=?
*/
}
//推荐:用多的一方来保存数据,减少数据库维护的次数
//保存数据,通过员工方保存数据(多对一操作数据)
@Test
public void Save2() {
Session session=sf.openSession();
session.beginTransaction();
//部门对象
Dept dept=new Dept();
dept.setDeptName("人事部");
//员工对象
Employee emp_zs=new Employee();
emp_zs.setEmpName("张三");
Employee emp_ls=new Employee();
emp_ls.setEmpName("李四");
//处理关系
emp_zs.setDept(dept);
emp_ls.setDept(dept);
//保存数据
//先保存一的一方,再保存多的一方,这样关系会自动维护(配置映射一定要正确)
session.save(dept);//保存部门下的所有员工
session.save(emp_zs);
session.save(emp_ls);
session.getTransaction().commit();
session.close();
/* Hibernate: insert into t_dept (deptName) values (?)
Hibernate: insert into t_employee (empName, salary, dept_Id) values (?, ?, ?)
Hibernate: insert into t_employee (empName, salary, dept_Id) values (?, ?, ?)
少生成2条update的sql
*/
}
}
6.hibernate.cfg.xml
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<!-- 通常,一个session-factory节点代表一个数据库 -->
<session-factory>
<!-- 1.数据库连接配置 -->
<property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
<property name="hibernate.connection.url">jdbc:mysql:///hib-demo</property>
<property name="hibernate.connection.username">root</property>
<property name="hibernate.connection.password">123456</property>
<!--数据库方法配置,hibernate在运行的时候,会根据不同的方言生成符合当前数据库语法的sql -->
<property name="hibernate.dialect">org.hibernate.dialect.MySQL5Dialect</property>
<!-- 2.其他相关配置 -->
<!--2.1显示hibernate在运行的时候执行的sql语句 -->
<property name="hibernate.show_sql">true</property>
<!-- 2.2格式化sql
<property name="hibernate.format_sql">true</property>-->
<!-- 2.3自动建表 -->
<property name="hibernate.hbm2ddl.auto">update</property>
<!-- 3.加载所有映射
<mapping resource="cn/itcast/a_hello/Employee.hbm.xml"/>-->
</session-factory>
</hibernate-configuration>