本文共 6412 字,大约阅读时间需要 21 分钟。
继承映射: 类有继承的概念, 表是没有继承的概念的, 但是可以体现这种关系
首先, 新建三个类, 分别是Animal类/Pig类/Bird类, 它们之间的关系是Pig类继承Animal类/Bird类继承Animal类, 然后建立映射关系
工程结构如图:
①单表继承映射(缺点: 出现冗余字段)
将这些属性存储在一张表中:
anId | anName | gender | weight | height | type |
1 | 八戒 | 1 | 300 | P | |
2 | 大鹏 | 1 | 10000 | B |
添加:
"Animal.hbm.xml"配置文件:
生成数据库表(1张表):
插入数据:
测试代码:
package com.rl.hiber.test;import org.hibernate.Session;import org.hibernate.Transaction;import org.junit.Test;import com.rl.hiber.model.Bird;import com.rl.hiber.model.Pig;import com.rl.hiber.utils.HibernateUtil;public class TestHibernate { @Test public void test1(){ Session session = HibernateUtil.getSessoion(); Transaction tx = session.beginTransaction(); try { Pig pig = new Pig(); pig.setAnName("天蓬元帅"); pig.setGender(1); pig.setWeight(300); session.save(pig); Bird bird = new Bird(); bird.setAnName("大鹏"); bird.setGender(1); bird.setHeight(10000); session.save(bird); tx.commit(); } catch (Exception e) { e.printStackTrace(); tx.rollback(); }finally{ HibernateUtil.closeResource(session); } }}
控制台输出:
Hibernate: insert into t_animal (an_name, gender, weight, type) values (?, ?, ?, 'p')Hibernate: insert into t_animal (an_name, gender, height, type) values (?, ?, ?, 'b')
数据库结果:
查询:
查询子类:
测试代码:
@Test public void test2(){ Session session = HibernateUtil.getSessoion(); try { Pig pig = (Pig) session.load(Pig.class, 1); System.out.println(pig.getAnName()+" "+pig.getWeight()); } catch (Exception e) { e.printStackTrace(); }finally{ HibernateUtil.closeResource(session); } }
控制台输出:
Hibernate: select pig0_.an_id as an_id1_0_0_, pig0_.an_name as an_name3_0_0_, pig0_.gender as gender4_0_0_, pig0_.weight as weight5_0_0_ from t_animal pig0_ where pig0_.an_id=? and pig0_.type='p'天蓬元帅 300
查询父类:
测试代码:
/** * load的延迟加载返回的是代理类, 所以无法完成多态(父类)查询 */ @Test public void test3(){ Session session = HibernateUtil.getSessoion(); try { Animal animal = (Animal) session.load(Animal.class, 1); if(animal instanceof Pig){ System.out.println("是猪"); }else{ System.out.println("不是猪"); } } catch (Exception e) { e.printStackTrace(); }finally{ HibernateUtil.closeResource(session); } } /** * get是急加载方式, 所以能够知道是Pig类型, 直接可以强转输出 */ @Test public void test4(){ Session session = HibernateUtil.getSessoion(); try { Animal animal = (Animal) session.get(Animal.class, 1); if(animal instanceof Pig){ System.out.println("是猪"); Pig pig = (Pig)animal; System.out.println(pig.getAnName() + " "+pig.getWeight()); }else{ System.out.println("不是猪"); } } catch (Exception e) { e.printStackTrace(); }finally{ HibernateUtil.closeResource(session); } }
get方式的控制台输出:
Hibernate: select animal0_.an_id as an_id1_0_0_, animal0_.an_name as an_name3_0_0_, animal0_.gender as gender4_0_0_, animal0_.weight as weight5_0_0_, animal0_.height as height6_0_0_, animal0_.type as type2_0_0_ from t_animal animal0_ where animal0_.an_id=?是猪天蓬元帅 300
②父子表继承映射(无冗余字段, 但效率比①较低)
顾名思义: 父类和子类各自一张表(父类产生父类的表, 子类产生子类的表)
"Animal1.hbm.xml"配置文件:
生成数据库表(3张表):
插入数据:
测试代码不变:
@Test public void test1(){ Session session = HibernateUtil.getSessoion(); Transaction tx = session.beginTransaction(); try { Pig pig = new Pig(); pig.setAnName("天蓬元帅"); pig.setGender(1); pig.setWeight(300); session.save(pig); Bird bird = new Bird(); bird.setAnName("大鹏"); bird.setGender(1); bird.setHeight(10000); session.save(bird); tx.commit(); } catch (Exception e) { e.printStackTrace(); tx.rollback(); }finally{ HibernateUtil.closeResource(session); } }
控制台输出:
Hibernate: insert into t_animal (an_name, gender) values (?, ?)Hibernate: insert into t_pig (weight, pid) values (?, ?)Hibernate: insert into t_animal (an_name, gender) values (?, ?)Hibernate: insert into t_bird (height, bid) values (?, ?)
数据库结果:
查询:
查询的方式跟①相同, 但是由于父子表的映射生成的表有多张, 所以查询时需要多张表连接查询, 效率较①低
Hibernate: select pig0_.pid as an_id1_0_0_, pig0_1_.an_name as an_name2_0_0_, pig0_1_.gender as gender3_0_0_, pig0_.weight as weight2_2_0_ from t_pig pig0_ inner join t_animal pig0_1_ on pig0_.pid=pig0_1_.an_id where pig0_.pid=?
Hibernate: select animal0_.an_id as an_id1_0_0_, animal0_.an_name as an_name2_0_0_, animal0_.gender as gender3_0_0_, animal0_1_.weight as weight2_2_0_, animal0_2_.height as height2_1_0_, case when animal0_1_.pid is not null then 1 when animal0_2_.bid is not null then 2 when animal0_.an_id is not null then 0 end as clazz_0_ from t_animal animal0_ left outer join t_pig animal0_1_ on animal0_.an_id=animal0_1_.pid left outer join t_bird animal0_2_ on animal0_.an_id=animal0_2_.bid where animal0_.an_id=?是猪天蓬元帅 300
③子表继承映射
"Animal2.hbm.xml"配置文件:
注意: Animal类也需要将anId改为String类型
数据表生成:
插入数据:
测试代码:
跟①相同
控制台输出结果:
Hibernate: insert into t_pig (an_name, gender, weight, an_id) values (?, ?, ?, ?)Hibernate: insert into t_bird (an_name, gender, height, an_id) values (?, ?, ?, ?)
数据库结果:
查询:
跟①相同