Hibernate (三)
1 一对多的单向
- 示例:一个已经存在的学生,新建一个班级,然后将该学生加入到该班级之下
- 设置inverse="false"
<?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>
<class name="com.xuweiwei.vo.Classes">
<id name="cid">
<generator class="native"></generator>
</id>
<property name="name"/>
<property name="description"/>
<!--
set元素描述了集合
name就是属性的名称
cascade:save-update保存或更新的时候对Student进行操作
inverse 是否维护关系:Classes是否维护和Student之间的关系
true 不维护关系
false 维护关系
default=false
-->
<set name="students" cascade="save-update" >
<!--
key代表外键
-->
<key>
<column name="cid"/>
</key>
<!--
建立了对象和对象之间的关联
-->
<one-to-many class="com.xuweiwei.vo.Student"/>
</set>
</class>
</hibernate-mapping>
- 测试代码:
/**
* 已经存在一个学生,新建一个班级,把该学生加入到该班级
*/
@Test
public void testSaveClasses_Build(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Student student = (Student) session.get(Student.class,1L);
Classes c = new Classes();
c.setName("Linux");
c.setDescription("Linux厉害");
c.getStudents().add(student);
session.save(c);
tx.commit();
}
- 示例:已经存在一个学生,已经存在一个班级,将该学生加入到该班级
/**
* 已经存在一个学生,已经存在一个班级,将该学生加入到该班级
* 将sid为2的学生,加入到cid=1的班级
*/
@Test
public void testExistStudentAndClassesBuildRealationship(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Student student = (Student) session.get(Student.class,2L);
Classes classes = (Classes) session.get(Classes.class,1L);
classes.getStudents().add(student);
tx.commit();
}
- 示例:将一个学生(存在)从一个班级(存在)转移到另一个班级(存在)
/**
* 将一个学生从一个班级转移到另一个班级
*/
@Test
public void testTransferClasses(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Student student1 = (Student) session.get(Student.class,1L);
Classes classes1 = (Classes) session.get(Classes.class,1L);
Classes classes2 = (Classes) session.get(Classes.class,2L);
classes1.getStudents().remove(student1);
classes2.getStudents().add(student1);
tx.commit();
}
/**
* 将一个学生从一个班级转移到另一个班级
*/
@Test
public void testTransferClasses(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Student student1 = (Student) session.get(Student.class,1L);
Classes classes2 = (Classes) session.get(Classes.class,2L);
classes2.getStudents().add(student1);
tx.commit();
}
- 示例:解除一个班级和所有的学生之间的关系
/**
* 解除一个班级和所有学生之间的关系
*/
@Test
public void testClassesRemoveAll(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Classes classes = (Classes) session.get(Classes.class,1L);
classes.setStudents(null);
tx.commit();
}
- 示例:解除一个班级和其下所有学生的关系,然后建立这个班级和其它学生的关系
/**
* 解除一个班级的和所有学生的关系,重新建立班级和其它学生的关系
*
*/
@Test
public void testRebuild(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Classes classes = (Classes) session.get(Classes.class,1L);
List<Student> studentList = (List<Student>) session.createSQLQuery("select * from student where cid != 1 ").addEntity(Student.class).list();
classes.setStudents(new HashSet<>(studentList));
tx.commit();
}
- 示例:先设置学生的外键为null,然后删除指定的班级信息
/**
* 将cid为1的班级
*/
@Test
public void testCascadeDelete(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Classes classes = (Classes) session.get(Classes.class,1L);
session.delete(classes);
tx.commit();
}
- 示例:删除班级和其下的所有学生
<!--
set元素描述了集合
name就是属性的名称
cascade:save-update保存或更新的时候对Student进行操作
inverse 是否维护关系:Classes是否维护和Student之间的关系
true 不维护关系
false 维护关系
default=false
-->
<set name="students" cascade="all-delete-orphan" >
<!--
key代表外键
-->
<key>
<column name="cid"/>
</key>
<!--
建立了对象和对象之间的关联
-->
<one-to-many class="com.xuweiwei.vo.Student"/>
</set>
/**
* 删除班级和其下的所有学生
*/
@Test
public void testCascadeDeleteAll(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Classes classes = (Classes) session.get(Classes.class,2L);
session.delete(classes);
tx.commit();
}
2 一对多的双向
- Student.java
package com.xuweiwei.vo;
import java.io.Serializable;
/**
* 学生
*/
public class Student implements Serializable{
private Long sid;//学生的ib
private String name;//学生的名称
private String description;//学生的描述
private Classes classes ;//一个学生属于一个班级
public Long getSid() {
return sid;
}
public void setSid(Long sid) {
this.sid = sid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Classes getClasses() {
return classes;
}
public void setClasses(Classes classes) {
this.classes = classes;
}
}
- Student.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 >
<class name="com.xuweiwei.vo.Student">
<id name="sid">
<generator class="increment"/>
</id>
<property name="name"/>
<property name="description"/>
<!--
column表示外键
-->
<many-to-one name="classes" class="com.xuweiwei.vo.Classes" column="cid" cascade="save-update"/>
</class>
</hibernate-mapping>
- Classes.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>
<class name="com.xuweiwei.vo.Classes">
<id name="cid">
<generator class="increment"></generator>
</id>
<property name="name"/>
<property name="description"/>
<!--
set元素描述了集合
name就是属性的名称
cascade:save-update保存或更新的时候对Student进行操作
inverse 是否维护关系:Classes是否维护和Student之间的关系
true 不维护关系
false 维护关系
default=false
-->
<set name="students" cascade="all-delete-orphan" >
<!--
key代表外键
-->
<key>
<column name="cid"/>
</key>
<!--
建立了对象和对象之间的关联
-->
<one-to-many class="com.xuweiwei.vo.Student"/>
</set>
</class>
</hibernate-mapping>
3 多对多操作
- 以学生和课程为例
3.1 配置hibernate多对多的环境
- hibernate.cfg.xml
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<!--
一个sessionFactory就代表一个数据库的描述
-->
<session-factory>
<!-- 链接数据库的用户名 -->
<property name="connection.username">root</property>
<!-- 链接数据库的密码 -->
<property name="connection.password">root</property>
<!-- 链接数据库的驱动 -->
<property name="connection.driver_class">
com.mysql.jdbc.Driver
</property>
<!-- 链接数据库的url -->
<property name="connection.url">
jdbc:mysql://localhost:3306/hibernate
</property>
<!--
方言
告诉hibernate用什么样的数据库,将来会生成什么样的sql语句
-->
<property name="dialect">
org.hibernate.dialect.MySQLDialect
</property>
<!--
hibernate对表的策略
validate 在hibernate容器启动的时候,根据映射文件和持久化类校验表
create 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表
create-drop 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表,销毁的时候删除表
update 检查,如果和映射文件不一致,则更新表的结构,如果没有表,则会创建表
-->
<property name="hbm2ddl.auto">update</property>
<!--
显示sql语句
-->
<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="current_session_context_class">thread</property>
<mapping resource="com/xuweiwei/vo/Student.hbm.xml"/>
<mapping resource="com/xuweiwei/vo/Course.hbm.xml"/>
</session-factory>
</hibernate-configuration>
- Student.java
package com.xuweiwei.vo;
import java.io.Serializable;
import java.util.Set;
public class Student implements Serializable {
private Long sid;
private String name;
private String description;
private Set<Course> courses;
public Long getSid() {
return sid;
}
public void setSid(Long sid) {
this.sid = sid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Set<Course> getCourses() {
return courses;
}
public void setCourses(Set<Course> courses) {
this.courses = courses;
}
}
- 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>
<class name="com.xuweiwei.vo.Student">
<id name="sid" length="5">
<generator class="native"/>
</id>
<property name="name" length="20"/>
<property name="description" length="50"/>
<!--
table表示中间表
-->
<set name="courses" table="student_course" cascade="save-update">
<!--
表示student在第三方表所对应外键
-->
<key>
<column name="sid"></column>
</key>
<many-to-many class="com.xuweiwei.vo.Course" column="cid"> </many-to-many>
</set>
</class>
</hibernate-mapping>
- Course.java
package com.xuweiwei.vo;
import java.io.Serializable;
import java.util.Set;
public class Course implements Serializable {
private Long cid;
private String name;
private String description;
private Set<Student> students ;
public Long getCid() {
return cid;
}
public void setCid(Long cid) {
this.cid = cid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Set<Student> getStudents() {
return students;
}
public void setStudents(Set<Student> students) {
this.students = students;
}
}
- Course.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>
<class name="com.xuweiwei.vo.Course">
<id name="cid" length="5">
<generator class="native"/>
</id>
<property name="name" length="20"/>
<property name="description" length="50"/>
<set name="students" table="student_course">
<key>
<column name="cid"></column>
</key>
<many-to-many class="com.xuweiwei.vo.Student" column="sid"> </many-to-many>
</set>
</class>
</hibernate-mapping>
- 测试代码:
package com.xuweiwei.test;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.junit.Test;
public class TestManyToMany {
@Test
public void testCreateTable(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
tx.commit();
}
}
3.2 多对多的操作
- 示例:保存学生信息的同时级联保存课程信息
/**
* 保存学生的同时保存课程
*/
@Test
public void testCreateStudentAndCourse(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Student student = new Student();
student.setName("许威威");
student.setDescription("java开发");
Course course1 = new Course();
course1.setName("Linux");
course1.setDescription("Linux如此之牛逼");
Course course2 = new Course();
course2.setName("java");
course2.setDescription("java就是如此之牛逼");
Set<Course> courses = new HashSet<>();
courses.add(course1);
courses.add(course2);
student.setCourses(courses);
session.save(student);
tx.commit();
}
- 示例:解除课程1和所有学生的关系
//解除课程1和所有学生的关系
@Test
public void testRealseAll(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Course course = (Course) session.get(Course.class,1L);
course.setStudents(null);
tx.commit();
}
- 示例:将学生从课程2转到课程1
/**
* 将学生从课程2转到课程1
*/
@Test
public void testStudentFromCourse2ToCourse1(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
//获取学生
Student student = (Student) session.get(Student.class,1L);
//获取课程1和课程2
Course course1 = (Course) session.get(Course.class,1L);
Course course2 = (Course) session.get(Course.class,2L);
//从学生中解除课程2的关系
student.getCourses().remove(course2);
//将学生转到课程1
student.getCourses().add(course1);
tx.commit();
}
- 示例:删除学生
/**
* 删除学生(并解除和课程的关系)
*/
@Test
public void testDeleteStudent(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
//获取学生
Student student = (Student) session.get(Student.class,1L);
session.delete(student);
tx.commit();
}
4 一对一操作
- 以人和身份证为例
4.1 环境的搭建
- hiberante.cfg.xml
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<!--
一个sessionFactory就代表一个数据库的描述
-->
<session-factory>
<!-- 链接数据库的用户名 -->
<property name="connection.username">root</property>
<!-- 链接数据库的密码 -->
<property name="connection.password">root</property>
<!-- 链接数据库的驱动 -->
<property name="connection.driver_class">
com.mysql.jdbc.Driver
</property>
<!-- 链接数据库的url -->
<property name="connection.url">
jdbc:mysql://47.93.11.136:3306/hibernate
</property>
<!--
方言
告诉hibernate用什么样的数据库,将来会生成什么样的sql语句
-->
<property name="dialect">
org.hibernate.dialect.MySQLDialect
</property>
<!--
hibernate对表的策略
validate 在hibernate容器启动的时候,根据映射文件和持久化类校验表
create 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表
create-drop 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表,销毁的时候删除表
update 检查,如果和映射文件不一致,则更新表的结构,如果没有表,则会创建表
-->
<property name="hbm2ddl.auto">update</property>
<!--
显示sql语句
-->
<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="current_session_context_class">thread</property>
<mapping resource="com/xuweiwei/vo/Person.hbm.xml"/>
<mapping resource="com/xuweiwei/vo/Identification.hbm.xml"/>
</session-factory>
</hibernate-configuration>
- Person.java
package com.xuweiwei.vo;
import java.io.Serializable;
import java.util.Set;
/**
* 人
*/
public class Person implements Serializable {
private Long pid;
private String name;
private String sex;
private Set<Identification> identifications;
public Long getPid() {
return pid;
}
public void setPid(Long pid) {
this.pid = pid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public Set<Identification> getIdentifications() {
return identifications;
}
public void setIdentifications(Set<Identification> identifications) {
this.identifications = identifications;
}
}
- Person.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>
<class name="com.xuweiwei.vo.Person">
<id name="pid">
<generator class="native"/>
</id>
<property name="name"/>
<property name="sex"/>
<set name="identifications" cascade="save-update">
<key column="pid"/>
<one-to-many class="com.xuweiwei.vo.Identification"/>
</set>
</class>
</hibernate-mapping>
- Identification.java
package com.xuweiwei.vo;
/**
* 身份证
*/
public class Identification {
private Long iid;
private String name;
private Person person;
public Long getIid() {
return iid;
}
public void setIid(Long iid) {
this.iid = iid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Person getPerson() {
return person;
}
public void setPerson(Person person) {
this.person = person;
}
}
- Identification.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>
<class name="com.xuweiwei.vo.Identification">
<id name="iid">
<generator class="native"/>
</id>
<property name="name"/>
<!--
unique外键唯一约束
-->
<many-to-one name="person" class="com.xuweiwei.vo.Person" unique="true" column="pid"/>
</class>
</hibernate-mapping>
4.2 一对一的操作
- 保存人信息的同时级联保存身份证信息
@Test
public void savePersonAndIdentification(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.getCurrentSession();
Transaction tx = session.beginTransaction();
Person p = new Person();
p.setName("许威威");
p.setSex("男");
Identification identification = new Identification();
identification.setName("许威威的身份证");
Set<Identification> identifications = new HashSet<>();
identifications.add(identification);
p.setIdentifications(identifications);
session.save(p);
tx.commit();
}
5 二级缓存
5.1 二级缓存的数据特点
- 公共的数据
- 不经常修改的数据
- 私密性不是很高的数据
5.2 二级缓存的生命周期
- 二级缓存的生命周期和SessionFactory紧密关联,当Hibernate容器启动的时候,二级缓存开始启动,当Hiberante容器卸载的时候,二级缓存停止。
5.3 二级缓存的分类(根据位置区分)
- 类级别的二级缓存
- 集合级别的二级缓存
5.4 Hibernate开启二级缓存的步骤
- Hibernate内部没有实现二级缓存,使用的是第三方缓存,所以需要配置
- 环境:班级和学生
- hibernate.cfg.xml
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<!--
一个sessionFactory就代表一个数据库的描述
-->
<session-factory>
<!-- 链接数据库的用户名 -->
<property name="connection.username">root</property>
<!-- 链接数据库的密码 -->
<property name="connection.password">root</property>
<!-- 链接数据库的驱动 -->
<property name="connection.driver_class">
com.mysql.jdbc.Driver
</property>
<!-- 链接数据库的url -->
<property name="connection.url">
jdbc:mysql://47.93.11.136:3306/hibernate
</property>
<!--
方言
告诉hibernate用什么样的数据库,将来会生成什么样的sql语句
-->
<property name="dialect">
org.hibernate.dialect.MySQLDialect
</property>
<!--
hibernate对表的策略
validate 在hibernate容器启动的时候,根据映射文件和持久化类校验表
create 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表
create-drop 每次当hibernate启动的时候,都会根据持久化类和映射文件创建表,销毁的时候删除表
update 检查,如果和映射文件不一致,则更新表的结构,如果没有表,则会创建表
-->
<property name="hbm2ddl.auto">update</property>
<!--
显示sql语句
-->
<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="current_session_context_class">thread</property>
<mapping resource="com/xuweiwei/vo/Classes.hbm.xml"/>
<mapping resource="com/xuweiwei/vo/Student.hbm.xml"/>
</session-factory>
</hibernate-configuration>
- Classes.java
package com.xuweiwei.vo;
import java.io.Serializable;
import java.util.Set;
/**
* 班级
*/
public class Classes implements Serializable{
private Long cid;
private String name;
private String description;
private Set<Student> students ;
public Long getCid() {
return cid;
}
public void setCid(Long cid) {
this.cid = cid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Set<Student> getStudents() {
return students;
}
public void setStudents(Set<Student> students) {
this.students = students;
}
}
- Classes.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>
<class name="com.xuweiwei.vo.Classes">
<id name="cid">
<generator class="increment"/>
</id>
<property name="name"/>
<property name="description"/>
<set name="students">
<key>
<column name="cid"/>
</key>
<one-to-many class="com.xuweiwei.vo.Student"></one-to-many>
</set>
</class>
</hibernate-mapping>
- Student.java
package com.xuweiwei.vo;
import java.io.Serializable;
/**
* 学生
*/
public class Student implements Serializable{
private Long sid;
private String name;
private String description;
private Classes classes;
public Long getSid() {
return sid;
}
public void setSid(Long sid) {
this.sid = sid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public Classes getClasses() {
return classes;
}
public void setClasses(Classes classes) {
this.classes = classes;
}
}
- 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>
<class name="com.xuweiwei.vo.Student">
<id name="sid">
<generator class="increment"/>
</id>
<property name="name"/>
<property name="description"/>
<many-to-one name="classes" column="cid" class="com.xuweiwei.vo.Classes"/>
</class>
</hibernate-mapping>
- 步骤:
- ①在hibernate.cfg.xml中配置二级缓存的供应商
<!--
提供二级缓存的供应商
-->
<property name="cache.provider_class">
org.hibernate.cache.EhCacheProvider
</property>
- ②在hibernate.cfg.xml中开启二级缓存
<!--
开启二级缓存
-->
<property name="cache.use_second_level_cache">true</property>
- ③
- 开启类级别的二级缓存
- 在hibernate.cfg.xml中配置(不推荐)
- 开启类级别的二级缓存
<!--
开启类级别的二级缓存
usage,开启二级缓存的策略
read-only 只读,把一个对象放入到二级缓存中不可以修改
read-write 读写 把一个对象放入到二级缓存中可以修改
class:类的全名
-->
<class-cache class="com.xuweiwei.vo.Classes" usage="read-only"/>
- 在对应的映射文件中配置
<?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>
<class name="com.xuweiwei.vo.Classes">
<cache usage="read-only"/>
<id name="cid">
<generator class="increment"/>
</id>
<property name="name"/>
<property name="description"/>
<set name="students">
<key>
<column name="cid"/>
</key>
<one-to-many class="com.xuweiwei.vo.Student"></one-to-many>
</set>
</class>
</hibernate-mapping>
- 开启集合级别的二级缓存
- 在<set>元素下配置
- 开启集合级别的二级缓存
<?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>
<class name="com.xuweiwei.vo.Classes">
<id name="cid">
<generator class="increment"/>
</id>
<property name="name"/>
<property name="description"/>
<set name="students" cascade="save-update">
<cache usage="read-only"/>
<key>
<column name="cid"/>
</key>
<one-to-many class="com.xuweiwei.vo.Student"></one-to-many>
</set>
</class>
</hibernate-mapping>
- ④测试和使用
- 类级别的二级缓存
- 证明二级缓存的存在
- 类级别的二级缓存
/**
* 先从一级缓存中查找数据,再从二级缓存中查找数据,最后从数据库中查找数据,然后将数据放入到一级缓存和二级缓存
*/
@Test
public void testGet(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.openSession();
Classes classes1 = (Classes) session.get(Classes.class,1L);
session.close();//一级缓存的数据没有了
session = sessionFactory.openSession();
Classes classes2 = (Classes) session.get(Classes.class,1L);//没有发出SQL语句
session.close();
}
- 在二级缓存的缓存策略是read-only的情况下,如果你修改数据,会报错
@Test
public void testGet(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.openSession();
Transaction tx = session.beginTransaction();
Classes classes1 = (Classes) session.get(Classes.class,1L);
classes1.setDescription("aa");
tx.commit();
session.close();
}

- 集合级别的二级缓存
- 证明二级缓存的存在
- 集合级别的二级缓存
@Test
public void testCollection(){
Configuration configuration = new Configuration().configure();
SessionFactory sessionFactory = configuration.buildSessionFactory();
Session session = sessionFactory.openSession();
Transaction tx = session.beginTransaction();
Classes classes1 = (Classes) session.get(Classes.class,1L);
Set<Student> students = classes1.getStudents();
for(Student s:students){
System.out.println(s.getName()+":"+s.getDescription());
}
System.out.println(sessionFactory.getStatistics().getCollectionLoadCount());
tx.commit();
session.close();
}
5.5 将二级缓存保存到磁盘上
- 在src下配置ehcache.xml
<ehcache xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../config/ehcache.xsd">
<diskStore path="e:\\TEMP1"/>
<defaultCache
maxElementsInMemory="12"
eternal="false"
timeToIdleSeconds="1200"
timeToLiveSeconds="1200"
overflowToDisk="false"
maxElementsOnDisk="10000000"
diskPersistent="false"
diskExpiryThreadIntervalSeconds="120"
memoryStoreEvictionPolicy="LRU"
/>
<Cache
name="com.xuweiwei.vo.Classes"
maxElementsInMemory="3"
eternal="false"
timeToIdleSeconds="120"
timeToLiveSeconds="120"
overflowToDisk="true"
maxElementsOnDisk="10000000"
diskPersistent="false"
diskExpiryThreadIntervalSeconds="120"
memoryStoreEvictionPolicy="LRU"
/>
</ehcache>
Hibernate (三)的更多相关文章
- 简单理解Hibernate三种状态的概念及互相转化
本文描述了Hibernate三种状态的概念及互相转化.Java对象的生命周期中有三种状态,而且互相转化.它们分别是临时状态,持久化状态,以及游离状态. AD:WOT2015 互联网运维与开发者大会 热 ...
- [转]hibernate三种状态详解
本文来自 http://blog.sina.com.cn/u/2924525911 hibernate 三种状态详解 (2013-04-15 21:24:23) 转载▼ 分类: hibernate ...
- hibernate三种状态
转自:http://www.cnblogs.com/xiaoluo501395377/p/3380270.html 学过hibernate的人都可能都知道hibernate有三种状态,transien ...
- hibernate(三) 一对多映射关系
序言 前面两节讲了hibernate的两个配置文件和hello world!.还有hibernate的一级缓存和三种状态,基本上hibernate就懂一点了,从这章起开始一个很重要的知识点,hiber ...
- Hibernate三种状态的转换
hibernate的状态 hibernate的各种保存方式的区(save,persist,update,saveOrUpdte,merge,flush,lock)及 对象的三种状态 hibernate ...
- Hibernate三种状态的区分,以及save,update,saveOrUpdate,merge等的使用 引自http://www.blogjava.net/TiGERTiAN/archive/2008/10/25/236519.html
Hibernate的对象有3种状态,分别为:瞬时态(Transient). 持久态(Persistent).脱管态(Detached).处于持久态的对象也称为PO(Persistence Object ...
- Hibernate(三)——框架中的关系映射
在设计数据库时我们会考虑,表与表之间的关系,例如我们前边经常提到的一对一,一对多,多对多关系,在数据库中我们通过外键,第三张表等来实现这些关系.而Hibernate时间实体类和数据库中的表进行的映射, ...
- hibernate 三种状态的转换
一.遇到的神奇的事情 使用jpa操作数据库,当我使用findAll()方法查处一个List的对象后,给对这个list的实体进行了一些操作,并没有调用update 或者 saveOrUpdate方法,更 ...
- SSH框架之-hibernate 三种状态的转换
一.遇到的神奇的事情 使用jpa操作数据库,当我使用findAll()方法查处一个List的对象后,给对这个list的实体进行了一些操作,并没有调用update 或者 saveOrUpdate方法,更 ...
- Hibernate三种状态,缓存,以及update更新问题
一. Hibernate中对象的三种状态 1. 瞬时状态(transient) 当我们通过Java的new关键字来生成一个实体对象时,这时这个实体对象就处于自由状态,此时该对象只是通过JVM获得了一块 ...
随机推荐
- [转载自阿里丁奇]各版本MySQL并行复制的实现及优缺点
MySQL并行复制已经是老生常谈,笔者从2010年开始就着手处理线上这个问题,刚开始两三年也乐此不疲分享,现在再提这个话题本来是难免"炒冷饭"嫌疑. 最近触发再谈这个话题,是 ...
- 厉害了,龙果!开源中国颁发了证书:GVP-码云最有价值开源项目
roncoo-pay (龙果支付系统) roncoo-pay是国内首款开源的互联网支付系统,其核心目标是汇聚所有主流支付渠道,打造一款轻量.便捷.易用,且集支付.资金对账.资金清结算于一体的支付系统, ...
- 使用Android-PullToRefresh实现下拉刷新功能
源代码:https://github.com/chrisbanes/Android-PullToRefresh 一. 导入类库 将Library文件夹作为Android项目Import到Eclipse ...
- CSS3对于盒中容纳不下的内容的显示——overflow属性
overflow属性 1.如果将overflow属性值设定为hidden,则超出容纳范围的文字将被隐藏起来. div{ overflow:hidden; } 2.如果将overflow属性值设定为sc ...
- poj_2195Going Home(最小费用最大流)
poj_2195Going Home(最小费用最大流) 标签: 最小费用最大流 题目链接 题意: 有n*m的矩阵,H表示这个点是一个房子,m表示这个点是一个人,现在每一个人需要走入一个房间,已经知道的 ...
- 通过案例理解position:relative和position:absolute
w3school过了HTML的知识之后,觉得要自己单纯地去啃知识点有点枯燥,然后自己也很容易忘记,所以便找具体的网站练手便补上不懂的知识点.position:relative和postion:abso ...
- cdn和反向代理
都是用来加速网站访问速度 cdn和反向代理的基本原理都是使用缓存,区别在于cdn部署在网络提供商的机房,使用户在请求网络服务时,可以从距离自己最近的网络提供商机房获取数据:而反向代理则部署在网站的中心 ...
- UVA 673 Parentheses Balance (栈)
题意描述: 给出一段只包含()和[]的字符串,判断是否合法,合法输出YES,不合法输出NO 规则: 1.该串为空,则合法 2.若A合法,B合法,则AB合法 3.若A合法,则(A)和[A]均合法 解题思 ...
- 《You dont know JS》值相关总结
值 一:和数组相关的几个需要关注的点 数组可以容纳任何类型的值. 数组声明时不需要预先设置大小.可以动态改变. 使用delete运算符可以将数组中的某个元素删除,但是这个操作不会改变数组的length ...
- windows server 2008使用nginx转发API异常解决办法
公司比较传统,一直使用的JSP做项目,没有遇到过跨域问题. 最近因为公司接到一个微信spa项目,因为考虑到项目需要调用老接口,斗胆选择nginx(1.12.1)做接口转发服务, 开发环境使用的win1 ...