您的位置:首页 > 其它

Hibernate---增删改查以及三种状态的转换

2018-03-05 11:48 211 查看
增删改查API:
增:session.save()
删:session.delete()
改:session.update()
查:session.get()或session.load()
使用这些API能完成数据库的增删改查,不过Hibernate拥有强大的缓存机制可以跳过这些API完成增删改查。
首先,我们需要了解在Hibernate中的三种状态:
1.瞬时状态     2.持久化状态    3.托管状态
这三种状态与session的缓存有着密切关系
瞬时状态就是刚new出来一个对象,还没有被保存到数据库中,持久化状态就是已经被保存到数据库中,托管状态就是数据库中有,但是session中不存在该对象,区分是否在数据库之中的关键词是是否有对应的主键。
public void First() {

Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
//增加一个班级
ClassRoom room=new ClassRoom();
room.setClassname("3班");
//这里是瞬时状态
session.save(room);
//room进入session缓存中,与session关联
room.setClassname("2班");
Transaction.commit();
session.close();
//session关闭,清理缓存room与session失去联系,变为托管状态
room.setClassname("4班");
}这个程序说明了三种状态的变化,那么程序执行的结果是什么?
控制台输出的sql语句是Hibernate: insert into ClassRoom (classname) values (?)
Hibernate: update ClassRoom set classname=? where cid=?数据库进行了save和update操作。
运行结果是


程序运行的流程:

执行ClassRoom room=new ClassRoom();
room.setClassname("3班");
//这里是瞬时状态
session.save(room);
处于瞬时状态的room,通过session.save()方法进入session缓存,同时session还为room对象进行了copy放入快照区。
room.setClassname("2班");
Transaction.commit();
room改变classname属性,事务提交,开始进行数据库操作。首先先在数据库insert快照区的room对象,然后再比较缓存区和快照区之间的是否有改变,如果有改变则进行update操作修改。session.close();
//session关闭,清理缓存room与session失去联系,变为托管状态
room.setClassname("4班");事务提交后,关闭session,session的缓存也得之清理,room失去了与session的联系,由持久化状态变为托管状态。
之后room对象无论进行什么操作都与session无关,自然和数据库操作无关。
结论:对象是持久化状态与对象是否进入session缓存区有关。
关于session的缓存有以下几个重要API:
session.clear()    session.evirt()    session.flush()
session.clear()就是清除session的所有缓存:Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
ClassRoom room=new ClassRoom();
room.setClassname("3班");
session.save(room);
session.clear();
//这一步之后,se
4000
ssion清理了缓存,room直接变成了托管状态
room.setClassname("2班");
Transaction.commit();
session.close();执行结果是:


简单的查找操作:public void Search() {
Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
ClassRoom room=session.get(ClassRoom.class, 1);//类对象类属性,id值
System.out.println(room.toString());
Transaction.commit();
session.close();
}结果:
Hibernate: select classroom0_.cid as cid1_0_0_, classroom0_.classname as classnam2_0_0_ from ClassRoom classroom0_ where classroom0_.cid=?
ClassRoom [cid=1, classname=1班]
删除操作:
数据库:

 目标是删去多余的三班public void Delete() {
Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
ClassRoom room=session.get(ClassRoom.class, 4);//类对象类属性,id值
session.delete(room);
Transaction.commit();
session.close();
}熟悉了Hibernate的缓存机制可以知道update操作交由持久化状态处理相当的方便,那么update方法是否显得多余。
update有一个重要的操作就是 将托管状态转化为持久态。
三种状态转化图:



update演示:
当前数据库:

     目标将多余的3班改为4班public void update() {
Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
ClassRoom room=new ClassRoom();
room.setCid(5);//设置了id,room为托管状态
session.update(room);//由此room变为了持久化状态
room.setClassname("4班");
Transaction.commit();
session.close();
}执行结果:Hibernate: update ClassRoom set classname=? where cid=?


上面讲的查询方法操作过于单一,下面介绍高级的查询方法。
HQL查询,HQL是hibernate专门用于查询数据的语句,有别于SQL,HQL跟接近于面向对象的思维方式。 
@Test
public void Query() {
Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
org.hibernate.Query query=session.createQuery("from ClassRoom where classname=?");
query.setString(0, "3班");
ClassRoom Result = (ClassRoom) query.uniqueResult();
System.out.println(Result);
Transaction.commit();
session.close();
}执行结果:
Hibernate: select classroom0_.cid as cid1_0_, classroom0_.classname as classnam2_0_ from ClassRoom classroom0_ where classroom0_.classname=?
ClassRoom [cid=3, classname=3班]


使用Criteria进行数据查询:Criteria 完全是面对对象在进行数据查询,将不再看到有sql语句的痕迹@Test
public void Criteria() {
Configuration configure = new Configuration().configure();

SessionFactory SessionFactory = configure.buildSessionFactory();

Session session = SessionFactory.openSession();

Transaction Transaction = session.beginTransaction();
org.hibernate.Criteria cr= session.createCriteria(ClassRoom.class);
List<ClassRoom> classrooms = cr.list();
for(ClassRoom room:classrooms) {
System.out.println(room);
}
Transaction.commit();
session.close();
}执行结果:Hibernate: select this_.cid as cid1_0_0_, this_.classname as classnam2_0_0_ from ClassRoom this_
ClassRoom [cid=1, classname=1班]
ClassRoom [cid=2, classname=2班]
ClassRoom [cid=3, classname=3班]
ClassRoom [cid=5, classname=4班]
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: