6.2.1 继承映射:采用subclass元素的继承映射

对于面向对象的程序设计语言,继承、多态是两个最基本的概念。Hibernate的继承映射可以理解两个持久化类之间的继承关系,例如老师和人之间的关系,老师继承了人,可以认为老师是一个特殊的人。如果对人进行查询,老师实例也将被得到------而无须关注人的实例,老师的实例在底层数据库的存储。

Hibernate支持几种继承映射策略,不管哪种继承映射策略,Hibernate的多态查询都可以运行良好。

采用subclass元素的继承映射:

在这种映射策略下,整个继承树的所有实例都将保存在同一个表内。因为将父子类的实例全部保存在同一个表内,因此需要在该表中额外增加一列,使用该列来区分每行记录到底是哪个类的实例------这个列被称为辨别者列

在这种映射策略下,使用<subclass.../>元素来映射子持久化类,使用<discriminator.../>元素来映射辨别者列。除此之外,每个类映射中都需要指定辨别者列的值。

我们先将test库里的表删除:

然后新建一个web工程,并编写代码:

HibernateUtil.java :

public class HibernateUtil
{
	public static final SessionFactory sessionFactory;
	
	static
	{
		try
		{
			//采用默认的hibernate.cfg.xml来启动一个Configuration的实例
			Configuration configuration = new Configuration()
				.configure();
			//由Configuration的实例来创建一个SessionFactory实例
			sessionFactory = configuration.buildSessionFactory();
		}
		catch (Throwable ex)
		{
			System.err.println("Initial SessionFactory creation failed." + ex);
			throw new ExceptionInInitializerError(ex);
		}
	}
	
	//ThreadLocal可以隔离多个线程的数据共享,因此不再需要对线程同步	
	public static final ThreadLocal<Session> session
		= new ThreadLocal<Session>();
	
	public static Session currentSession()
		throws HibernateException
	{
		Session s = session.get();
		//如果该线程还没有Session,则创建一个新的Session
		if (s == null)
		{
			s = sessionFactory.openSession();
			//将获得的Session变量存储在ThreadLocal变量session里
			session.set(s);
		}
		return s;
	}
	
	public static void closeSession()
		throws HibernateException 
	{
		Session s = session.get();
		if (s != null)
			s.close();
		session.set(null);
	}
}
Person.java :

public class Person {
	
	private int id;
	private String name;
	private String gender;
	private Address address;//组件属性
	
	public int getId() {
		return id;
	}
	public void setId(int id) {
		this.id = id;
	}
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getGender() {
		return gender;
	}
	public void setGender(String gender) {
		this.gender = gender;
	}
	public Address getAddress() {
		return address;
	}
	public void setAddress(Address address) {
		this.address = address;
	}
	
}
Address.java :

public class Address {
	
	private String detail;
	private String zip;
	private String country;
	
	public Address() {
		
	}
	public Address(String detail, String zip, String country) {
		this.detail = detail;
		this.zip = zip;
		this.country = country;
	}
	
	public String getDetail() {
		return detail;
	}
	public void setDetail(String detail) {
		this.detail = detail;
	}
	public String getZip() {
		return zip;
	}
	public void setZip(String zip) {
		this.zip = zip;
	}
	public String getCountry() {
		return country;
	}
	public void setCountry(String country) {
		this.country = country;
	}
	
}
Employee.java :

public class Employee extends Person{
	
	private String title;//职位属性
	private double salary;
	private Set<Customer> customers=new HashSet<Customer>();
	private Manager manager;
	
	public Employee() {
		
	}
	public Employee(String title, double salary) {
		this.title = title;
		this.salary = salary;
	}
	
	public String getTitle() {
		return title;
	}
	public void setTitle(String title) {
		this.title = title;
	}
	public double getSalary() {
		return salary;
	}
	public void setSalary(double salary) {
		this.salary = salary;
	}
	public Set<Customer> getCustomers() {
		return customers;
	}
	public void setCustomers(Set<Customer> customers) {
		this.customers = customers;
	}
	public Manager getManager() {
		return manager;
	}
	public void setManager(Manager manager) {
		this.manager = manager;
	}
	
	
}
Manager.java :

public class Manager extends Employee{
	
	private String department;//经理的管辖部门
	private Set<Employee> employees=new HashSet<Employee>();
	
	public Manager() {
		
	}
	public Manager(String department) {
		super();
		this.department = department;
	}
	
	public String getDepartment() {
		return department;
	}
	public void setDepartment(String department) {
		this.department = department;
	}
	public Set<Employee> getEmployees() {
		return employees;
	}
	public void setEmployees(Set<Employee> employees) {
		this.employees = employees;
	}
	
	
}
Customer.java :

public class Customer extends Person{
	
	private String comments;//顾客评论
	private Employee employee;//和员工保持关联关系的属性
	
	public Customer() {
		
	}
	public Customer(String comments) {
		this.comments = comments;
	}
	
	public String getComments() {
		return comments;
	}
	public void setComments(String comments) {
		this.comments = comments;
	}
	public Employee getEmployee() {
		return employee;
	}
	public void setEmployee(Employee employee) {
		this.employee = employee;
	}
	
}
Person.hbm.xml :

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC 
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    
<hibernate-mapping package="db.domain">
    <class name="Person" table="persons" discriminator-value="普通人">
        <id name="id" column="id">
            <generator class="identity"/>
        </id>
        <discriminator column="kinds" type="string"/>
        <property name="name" type="string"/>
        <property name="gender" type="string"/>
        <component name="address">
            <property name="detail"/>
            <property name="zip"/>
            <property name="country"/>
        </component>
        
        <subclass name="Employee" discriminator-value="雇员">
            <property name="title"/>
            <property name="salary"/>
            <set name="customers" inverse="true">
                <key column="employee_id"/>
                <one-to-many class="Customer"/>
            </set>
            <many-to-one name="manager" column="manager_id"/>
            <subclass name="Manager" discriminator-value="经理">
                <property name="department"/>
                <set name="employees" inverse="true">
                    <key column="manager_id"/>
                    <one-to-many class="Employee"/>
                </set>
            </subclass>
        </subclass>
        <subclass name="Customer" discriminator-value="顾客">
            <property name="comments"/>
            <many-to-one name="employee" column="employee_id"/>
        </subclass>
    </class>
</hibernate-mapping>
PersonManager.java :

public class PersonManager {

	public static void main(String[] args) {
		
		PersonManager mgr = new PersonManager();
		mgr.createAndStorePerson();
		HibernateUtil.sessionFactory.close();
	}
	
	private void createAndStorePerson(){
		Session session = HibernateUtil.currentSession();
		Transaction tx = session.beginTransaction();
		//创建一个普通员工
		Employee zhu = new Employee();
		//设置员工的基本属性
		zhu.setName("老朱");
		zhu.setTitle("项目组长");
		zhu.setGender("男");
		zhu.setSalary(4500);
		//设置员工的组件属性
		zhu.setAddress(new Address("广州","523034","中国"));
		//创建第二个员工
		Employee zhang = new Employee();
		//设置该员工的基本属性
		zhang.setName("张美丽");
		zhang.setTitle("项目分析");
		zhang.setGender("女");
		zhang.setSalary(5500);
		//设置该员工的组件属性
		zhang.setAddress(new Address("广州","523034","中国"));
		//创建一个经理对象
		Manager grace = new Manager();
		//设置经理对象的基本属性
		grace.setName("Grace");
		grace.setTitle("项目经理");
		grace.setGender("女");
		grace.setSalary(12000);
		//设置经理的组件属性
		grace.setAddress(new Address("加州","523034","美国"));
		//设置经理的管辖部门属性
		grace.setDepartment("研发部");
		//设置第二个员工和grace之间的关联关系
		zhang.setManager(grace);
		//创建一个Customer对象
		Customer he = new Customer();
		//设置Customer对象的基本属性
		he.setName("小贺");
		he.setGender("男");
		//设置Customer对象的组件属性
		he.setAddress(new Address("湖南","233034","中国"));
		he.setComments("喜欢购物");
		//建立Customer对象和grace对象的关联关系
		he.setEmployee(grace);
		//创建一个普通Person对象
		Person lee = new Person();
		//设置Person对象的基本属性
		lee.setName("Yeeku");
		lee.setGender("男");
		//设置Person对象的组件属性
		lee.setAddress(new Address("天河","434333","中国"));
		//持久化所有实体。
		session.save(lee);
		session.save(grace);
		session.persist(zhu);
		session.persist(zhang);
		session.save(he);
		tx.commit();
		HibernateUtil.closeSession();
	}

}
运行PersonManager.java,查看数据库:



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值