第23章 J2EE SSH基础学习-Hibernate概述-1

Hibernate最主要是解决先进的面向对象编程方式与相对麻烦落后的关系型数据库之间的开发存在着冲突,然后我们为了简化对象和记录之间的转化而开发出的一种工具。Hibernate就是简单的对象关系映射工具之一。同时也是现如今相对成熟的重量级全自动开发框架之一:

 概念完整,使用困难,调试对开发人员要求高,谨慎使用


hibernate主要工作时创建一个SessionFactory,然后我们所有的操作都是基于sessionFactory工厂模式下的事物提交工作。

Hibernate控制不是很容易,因为同一段代码。可能因为你导入的hibernate的jar包不同,而发生异常(最头疼),但是所幸现在基本解决了。大概就是我们在Eclipse或者myEclipse中创建工程的时候,喜欢选择默认的jdk7.0版本,然后我们导入的hibernate如果是低版本的话可能可以兼容,所以代码没问题,但是如果我们导入的是hibernate高版本的jar包,变回发生无法创建不支持等等情况。这个很多朋友都给解决方案,我就不多写了,最直接的方法就是将自己的jdk改为1.8 之后的便可。或者在网上找hibernate低版本替代也可以。

嗯,本章知识开始,就不多说了;下面是一个学生餐卡信息绑定的hibernate程序案例:

首先我们看一下 单实例模式(1对1)学生信息CURD

Student.java:

/**
 * 工  程   名:HibernateDemo-OneEntity-CRUD	<br>
 * 文  件   名:Student.java	<br>
 * 工具包名:edu.fjnu.domain	<br>
 * 功能描述:TODO	<br>
 * 创建时间:2018年5月25日 下午8:40:38	<br>
 * 版本信息:V1.0
 * @创建人:Zhou Kailun	
 */
package edu.fjnu.domain;

/**
 * 类名:Student	<br>
 * 功能描述:	<br> 
 * 创建日期:2018年5月25日 下午8:40:38	<br>
 * 修改备注:
 * @作者信息:Zhou kailun	<br>
 */
public class Student {
	/**学生学号*/
	private Integer stuNo;
	/**学生姓名*/
	private String stuName;
	/**学生年龄*/
	private Integer stuAge;
	/**<p>构造函数:</p><br><br>
	 * <p>描述:</p><br> 
	 */
	public Student() {
		// TODO Auto-generated constructor stub
	}
	public Integer getStuNo() {
		return stuNo;
	}
	public void setStuNo(Integer stuNo) {
		this.stuNo = stuNo;
	}
	public String getStuName() {
		return stuName;
	}
	public void setStuName(String stuName) {
		this.stuName = stuName;
	}
	public Integer getStuAge() {
		return stuAge;
	}
	public void setStuAge(Integer stuAge) {
		this.stuAge = stuAge;
	}
	@Override
	public String toString() {
		return "Student [stuNo=" + stuNo + ", stuName=" + stuName + ", stuAge="
				+ stuAge + "]";
	}
	

}

Student.hbm.xml 学生信息配置文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd" >
<hibernate-mapping package="edu.fjnu.domain">
	<!-- 学生信息与数据库匹配 -->
	<class name="Student" table="tbl_student2">
		<id name="stuNo" column="stu_no" type="java.lang.Integer"></id>
		<property name="stuName" column="stu_name" type="java.lang.String" not-null="true"></property>
		<property name="stuAge" column="stu_age" type="java.lang.Integer"></property>
		
	</class>
</hibernate-mapping>

然后是 hibernate.cfg.xml 

<!--
  ~ Hibernate, Relational Persistence for Idiomatic Java
  ~
  ~ License: GNU Lesser General Public License (LGPL), version 2.1 or later.
  ~ See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
  -->
<!DOCTYPE hibernate-configuration PUBLIC
	"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
	"http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">

<hibernate-configuration>
	<!-- 操作的最终目标只是为了创建一个能够创建session的sessionFactory -->
	<session-factory>
		<!-- 数据库连接信息:数据位置信息, 用户名,密码,驱动位置 -->
		<property name="connection.url">
			jdbc:mysql://localhost:3306/test
		</property>
		<property name="connection.username">tester</property>
		<property name="connection.password">123456</property>
		<property name="connection.driver_class">
			com.mysql.jdbc.Driver
		</property>
		
		<!--  数据方言:针对某一数据库进行优化  -->
		<property name="dialect">
			org.hibernate.dialect.MySQL5Dialect
		</property>
		
		<!-- 要不要打印数据库语句,以及格式化数据库语句 -->
		<property name="show_sql">true</property>
		<property name="format_sql">true</property>
		<mapping resource="edu/fjnu/domain/Student.hbm.xml" />
	</session-factory>	
	 
</hibernate-configuration>

最后是测试代码:

package edu.fjnu.test;

import static org.junit.Assert.*;

import java.util.List;

import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.TransactionException;
import org.hibernate.cfg.Configuration;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import edu.fjnu.domain.Student;

public class StudentCRUDTester {
	private SessionFactory factory;
	private Session session;
	@Before
	public void setUp() throws Exception {
		System.out.println("test prepared.....");
		Configuration config=new Configuration();//构建一个配置器
		config.configure("/edu/fjnu/config/hibernate.cfg.xml");
		factory =config.buildSessionFactory();
		session=factory.openSession();
	}

	@After
	public void tearDown() throws Exception {
		System.out.println("test clear....");
		if(session.isOpen())
			session.close(); 
		if(!factory.isClosed())
			factory.close();
	}
	 
	@Test
	public void addStudent(){
		System.out.println("test add Student。。。");
		
		Student stu=new Student();
		stu.setStuNo(1);
		stu.setStuName("mery");
		stu.setStuAge(12);
		
		Student stu2=new Student();
		stu2.setStuNo(2);
		stu2.setStuName("mike");
		stu2.setStuAge(22);
		
		Transaction transaction=session.beginTransaction();
		
		try{
			session.save(stu);
			session.save(stu2);
			transaction.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			transaction.rollback();
		}
	}
	@Test
	public void getStudentById(){
		Transaction trans=session.beginTransaction();
		try{
			Student stu=(Student)session.get(Student.class,2);
			System.out.println(stu);
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}
	@Test
	public void updateStudent(){
		Transaction trans=session.beginTransaction();
		try{
			Student stu=(Student)session.get(Student.class, 2);
			stu.setStuAge(stu.getStuAge()+2);
			session.saveOrUpdate(stu);
			
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}
	
	public void removeStudent(){
		Transaction trans=session.beginTransaction();
		try{
			//get方法是获得这个学生的所有属性,成本比较高,删除操作不建议使用get
			Student stu=(Student)session.load(Student.class, 2); 
			session.delete(stu);
			
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}
	
	@Test
	public void loadStudents(){
		Transaction trans=session.beginTransaction();
		try{
			String hql="from Student s where s.stuAge>=11 order by s.stuNo desc";//hql:hibernate query language
			
			Query query=session.createQuery(hql);
			List<Student> stus=query.list();
			
			for(Student stu:stus){
				System.out.println(stu);
			}
			
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}

}

2   接下来是 一对多(1对n)实例代码:

学生-餐卡实例:一个学生可以有多张餐卡,但是一张餐卡只属于一个学生

Student.java

/**
 * 工  程   名:HibernateDemo-OneEntity-CRUD	<br>
 * 文  件   名:Student.java	<br>
 * 工具包名:edu.fjnu.domain	<br>
 * 功能描述:TODO	<br>
 * 创建时间:2018年5月25日 下午8:40:38	<br>
 * 版本信息:V1.0
 * @创建人:Zhou Kailun	
 */
package edu.fjnu.domain;

import java.util.HashSet;
import java.util.Set;

/**
 * 类名:Student	<br>
 * 功能描述:	<br> 
 * 创建日期:2018年5月25日 下午8:40:38	<br>
 * 修改备注:
 * @作者信息:Zhou kailun	<br>
 */
public class Student {
	/**学生学号*/
	private Integer stuNo;
	/**学生姓名*/
	private String stuName;
	/**学生年龄*/
	private Integer stuAge;
	/**学生餐卡*/
	private Set<DinnerCard> cards=new HashSet<DinnerCard>();
	/**<p>构造函数:</p><br><br>
	 * <p>描述:</p><br> 
	 */
	public Student() {
		// TODO Auto-generated constructor stub
	}
	public Integer getStuNo() {
		return stuNo;
	}
	public void setStuNo(Integer stuNo) {
		this.stuNo = stuNo;
	}
	public String getStuName() {
		return stuName;
	}
	public void setStuName(String stuName) {
		this.stuName = stuName;
	}
	public Integer getStuAge() {
		return stuAge;
	}
	public void setStuAge(Integer stuAge) {
		this.stuAge = stuAge;
	}
	public Set<DinnerCard> getCards() {
		return cards;
	}
	public void setCards(Set<DinnerCard> cards) {
		this.cards = cards;
	}
	@Override
	public String toString() {
		return "Student [stuNo=" + stuNo + ", stuName=" + stuName + ", stuAge="
				+ stuAge + ", cards=" + cards + "]";
	}
	
}
DinnerCard.java  :
/**
 * 工  程   名:HibernateDemo-OneToMany	<br>
 * 文  件   名:DinnerCard.java	<br>
 * 工具包名:edu.fjnu.domain	<br>
 * 功能描述:TODO	<br>
 * 创建时间:2018年5月26日 下午4:20:52	<br>
 * 版本信息:V1.0
 * @创建人:Zhou Kailun	
 */
package edu.fjnu.domain;

/**
 * 类名:DinnerCard	<br>
 * 功能描述:	<br> 
 * 创建日期:2018年5月26日 下午4:20:52	<br>
 * 修改备注:
 * @作者信息:Zhou kailun	<br>
 */
public class DinnerCard {
	/**卡号*/
	private Integer cardNo;
	/**金额*/
	private Integer money;
	/**餐卡所属学生:*/
	private Student owner;
	/**<p>构造函数:</p><br><br>
	 * <p>描述:</p><br> 
	 */
	public DinnerCard() {
		// TODO Auto-generated constructor stub
	}
	public Integer getCardNo() {
		return cardNo;
	}
	public void setCardNo(Integer cardNo) {
		this.cardNo = cardNo;
	}
	public Integer getMoney() {
		return money;
	}
	public void setMoney(Integer money) {
		this.money = money;
	}
	 
	public Student getOwner() {
		return owner;
	}
	public void setOwner(Student owner) {
		this.owner = owner;
	}
	@Override
	public String toString() {
		return "DinnerCard [cardNo=" + cardNo + ", money=" + money + "]";
	}

}

Student.hbm.xml  

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd" >
<hibernate-mapping package="edu.fjnu.domain">
	<!-- 学生信息与数据库匹配 -->
	<class name="Student" table="tbl_student2">
		<id name="stuNo" column="stu_no" type="java.lang.Integer"></id>
		<property name="stuName" column="stu_name" type="java.lang.String" not-null="true"></property>
		<property name="stuAge" column="stu_age" type="java.lang.Integer"></property>
		<!-- 提供各种各样的条件告诉hibernate以获得cards这个集合类型
			1:table="tbl_dinner_card";:请到这张表去找cards
			2:<key><column name="owner"/></key>:请根据这章表的owner这个外建去找
			3:@stuNo//隐含条件
			select * from tbl_dinner_card where stu_no=?
		 	4:<one-to-many class="DinnerCard"/>:可以参照dinnerCard这个类的映射定义去吧记录封装成对象
			5: cascade="all" 级联操作。
			6: inverst="true" 关系的维护:一方不维护,多方维护关系
		 	7:fetch="join" 生成数据库语句不分开 
		 -->
		<set name="cards" table="tbl_dinner_card" cascade="all" inverse="true" fetch="join">
			<key>
				<column name="stu_no" not-null="true"></column>
			</key>
			<one-to-many class="DinnerCard"/>
		</set>
	</class>
</hibernate-mapping>

DinnerCard.hbm.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd" >
<hibernate-mapping package="edu.fjnu.domain">
	<class name="DinnerCard" table="tbl_dinner_card">
		<id name="cardNo" column="card_no" type="java.lang.Integer">
			<!-- 主键生成策略,默认是assigned,由用户赋予,保证主键唯一性 -->
			<generator class="increment"></generator>
		</id>
		<property name="money" column="money" type="java.lang.Integer"></property>
		
		<!-- 
			1:class="Student" 
			select * from tbl_student2
			2:column="stu_no"
			select * from tbl_student2 where stu_no=@stu_no
		 -->
		<many-to-one name="owner" class="Student" column="stu_no"></many-to-one>
		 
	</class>
</hibernate-mapping>

Hibernate.cfg.xml 将餐卡配置信息加入即可:

<mapping resource="edu/fjnu/domain/DinnerCard.hbml.xml" />

最后是测试代码:只完成了增加 查询,其他待续:

package edu.fjnu.test;

import static org.junit.Assert.*;

import java.util.List;

import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.TransactionException;
import org.hibernate.cfg.Configuration;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import edu.fjnu.domain.DinnerCard;
import edu.fjnu.domain.Student;

public class StudentCRUDTester {
	private SessionFactory factory;
	private Session session;
	@Before
	public void setUp() throws Exception {
		System.out.println("test prepared.....");
		Configuration config=new Configuration();//构建一个配置器
		config.configure("/edu/fjnu/config/hibernate.cfg.xml");
		factory =config.buildSessionFactory();
		session=factory.openSession();
	}

	@After
	public void tearDown() throws Exception {
		System.out.println("test clear....");
		if(session.isOpen())
			session.close(); 
		if(!factory.isClosed())
			factory.close();
	}
	 
	@Test
	public void addStudent(){
		System.out.println("test add Student。。。");
		
		Student stu=new Student();
		stu.setStuNo(4);
		stu.setStuName("张丽");
		stu.setStuAge(12);
		
		DinnerCard card=new DinnerCard();
		card.setMoney(200);
		
		DinnerCard card2=new DinnerCard();
		card2.setMoney(500);
		
		stu.getCards().add(card);
		stu.getCards().add(card2);
		
		card.setOwner(stu);
		card2.setOwner(stu);
		
		Transaction transaction=session.beginTransaction();
		
		try{
			session.save(stu); 
			transaction.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			transaction.rollback();
		}
	}
	@Test
	public void getStudentById(){
		Transaction trans=session.beginTransaction();
		try{
			Student stu=(Student)session.get(Student.class,3);
			
			System.out.println(stu);
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}
	 
	@Test
	public void loadStudents(){
		Transaction trans=session.beginTransaction();
		try{
			String hql="from Student s where s.stuAge>=11 order by s.stuNo desc";//hql:hibernate query language
			Query query=session.createQuery(hql);
			List<Student> stus=query.list();
			
			for(Student stu:stus){
				System.out.println(stu);
			}
			
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}
	@Test
	public void loadDinnerCards(){
		Transaction trans=session.beginTransaction();
		try{
			 String hql2="from DinnerCard dc where dc.money>=200 and dc.owner.stuName like '%张%'";
			Query query=session.createQuery(hql2);
			List<DinnerCard> cards=query.list();
			
			for(DinnerCard card:cards){
				System.out.println(card);
			}
			
			trans.commit();
		}catch(TransactionException e){
			e.printStackTrace();
			trans.rollback();
		}
	}

}


猜你喜欢

转载自blog.csdn.net/qq_36346496/article/details/80462440