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获得了一块 ...
随机推荐
- 2017 年的 人生 hard 模式终于结束了,2018年回归初心(二)
今天周末, 深圳的天气简直好的不像话.好了,我们继续之前的话题往下聊. >>>猎头 : 关于猎头这个行业,以笔者的感觉来说 一般你工作年限未超过三年的话,你是很难遇到猎头来推送你的简 ...
- python 单下划线/双下划线使用总结
文章转自:http://blog.csdn.net/pfm685757/article/details/45918575
- 初入python 用户输入,if,(while 循环)
python 基础 编译型: 一次性将所有程序编译成二进制文件. 缺点:开发效率低,不能跨平台 优点:运行速度快. :c ,c++语言 等等.... 解释行:当程序执行时,一行一行的解释. 优点:开发 ...
- kafka Topic 与 Partition
Topic在逻辑上可以被认为是一个queue队列,每条消息都必须指定它的topic,可以简单理解为必须指明把这条消息放进哪个queue里.为 了使得Kafka的吞吐率可以水平扩展,物理上把topic分 ...
- Codefoces 723A The New Year: Meeting Friends
A. The New Year: Meeting Friends time limit per test:1 second memory limit per test:256 megabytes in ...
- hackerrank DFS Edges
瞬间移动 题意:要求构造一个图,使其dfs树中有t条树边,b条返祖边,f条前向边,c条其他边. 膜了题解才会,好神啊. 考虑所有结点的深度之和,这个值必须介于$[max(b,f+t),C^{2}_{n ...
- [51nod1443]路径和树
给定一幅无向带权连通图G = (V, E) (这里V是点集,E是边集).从点u开始的最短路径树是这样一幅图G1 = (V, E1),其中E1是E的子集,并且在G1中,u到所有其它点的最短路径与他在G中 ...
- UESTC1599-wtmsb-优先队列
wtmsb Time Limit: 1000/100MS (Java/Others) Memory Limit: 131072/131072KB (Java/Others) 这天,AutSky_Jad ...
- Codeforces Round #280 (Div. 2)_C. Vanya and Exams
C. Vanya and Exams time limit per test 1 second memory limit per test 256 megabytes input standard i ...
- 二 @ResponseBody用法
@ResponseBody底层是通过response.getwriter()方法将数据写回前 台 @ResponseBody @RequestMapping (value="/queryLi ...