hibernate 一級緩存:(緩存的是實體對象)
一級緩存很短和session的生命週期一致,一級緩存也叫session級的緩存或事務緩存
哪些方法支持一級緩存:
*get()
*load()
*iterate() (查詢實體對象)
如何管理一級緩存:
* session.clear() session.evict()
如何避免一次性大量的實體數據入庫導致內存溢出
*先flush,再clear
如果數據量特別大,考慮採用jdbc實現,如果jdbc也不能滿足要求,可以考慮採用數據庫本身的特定導入工具
一.Load測試:在同一個session中發出兩次load查詢
Student sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
在同一個session中發出兩次load查詢,第一次load的時候不會去查詢數據庫,因爲他是LAZY的,當使用的時候纔去查詢數據庫,第二次load的時候也不會,當使用的時候也不會查詢數據庫,因爲他在緩存裏找到,不會發出sql
Load測試:開啓兩個session中發出兩次load查詢
Student sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
sessioin.close();
………..
sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
開啓兩個session中發出兩次load查詢,第一次load的時候不會去查詢數據庫,因爲他是LAZY的,當使用的時候纔去查詢數據庫,第二次load的時候也不會,當使用的時候查詢數據庫,因爲session間不能共享一級緩存的數據,因爲他會隨session的生命週期存在和消亡
二.Get測試:在同一個session中發出兩次get查詢
Student sutdent =(Student)session.get(Student.class,1);
System.out.println(student.getName());
sutdent = (Student)session.get(Student.class,1);
System.out.println(student.getName());
在同一個session中發出兩次get查詢,第一次get的時候去查詢數據庫,第二次get的時候不會查詢數據庫,因爲他在緩存裏找到,不會發出sql
三.iterate測試:在同一個session中發出兩次iterator查詢
Student student = (Student)session.createQuery(“from Student swhere s.id=1”).iterate().next();
System.out.println(student.getName());
student = (Student)session.createQuery(“from Student s wheres.id=1”).iterate().next();
System.out.println(student.getName());
在同一個session中發出兩次iterator查詢,第一次iterate().next()的時候會發出查詢id的sql,使用的時候會發出相應的查詢實體對象,第二次iterate().next()的時候會發出查詢id的sql,不會發出查詢實體對象的sql,因爲iterate使用緩存,不會發出sql
四.Iterate查詢屬性測試:同一個session中發出兩次查詢屬性
String name = (String)session.createQuery(“select s.name fromStudent s where s.id=1”).iterate().next();
System.out.println(name);
String name = (String)session.createQuery(“select s.name fromStudent s where s.id=1”).iterate().next();
System.out.println(name);
在同一個session中發出兩次查詢屬性,第一次iterate().next()的時候會發出查詢屬性的sql,第二次iterate().next()的時候會發出查詢屬性的sql,iterate查詢普通屬性,一級緩存不會緩存,所以會發出sql
五.同一個session中先save,再發出load查詢save過的數據
Student stu = new Student();
stu.setName(“王五”);
Serializableid = session.save(stu);
Student sutdent = (Student)session.load(Student.class,id);
System.out.println(student.getName());
save的時候,他會在緩存裏放一份,不會發出sql,因爲save是使用緩存的
六.同一個session中先調用load查詢,然後執行sessio.clear()或session.evict(),再調用load查詢
Student sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
session.clear();
Student sutdent = (Student)session.load(Student.class,1);
System.out.println(student.getName());
sessio.clear()或session.evict()可以管理一級緩存,一級緩存無法取消,但可以管理.
上面的語句都會發出sql 因爲一級緩存中的實體被清除了
七.向數據庫中批量加入1000條數據
for(int i=0;i<1000;i++){
Student student = new Student();
student.setName(“s” + i);
session.save(student);
//每20條數據就強制session將數據持久化,同時清除緩存,避免大量數據造成內存溢出
if( i %20 == 0 ){
session.flush();
session.clear();