不是吧 你这个是list和iterate的不同吧
在hibernate中,如果使用了延迟加载(比如常见的load方法),那么除访问主键以外的其它属性时,
就会去访问数据库(假设不考虑hibernate的一级缓存),此时session是不允许被关闭。
5个最常问的几个Hibernate面试问题,不一定你都能回答:
1.实体对象在Hibernate中如何进行状态迁移?
实体对象的状态及转化:
有了上面关于Hibernate缓存的知识,我们再来介绍实体对象的状态就非常容易理解了。
A:自由态对象:(临时状态-transient)
当我们通过Java的new关键字来生成一个实体对象时,这时这个实体对象就处于自由状态,如下:
Customer customer=new Customer(“zx”,27,images);
这时customer对象就处于自由状态,为什么说customer对象处于自由状态呢?这是因为,此时customer只是通过JVM获得了一块内存空间,还并没有通过Session对象的save()方法保存进数据库,因此也就还没有纳入Hibernate的缓存管理中,也就是说customer对象现在还自由的游荡于Hibernate缓存管理之外。所以我们可以看出自由对象最大的特点就是,在数据库中不存在一条与它对应的记录。
B:持久化对象: Persistent(持久态)
持久化对象就是已经被保存进数据库的实体对象,并且这个实体对象现在还处于Hibernate的缓存管理之中。这是对该实体对象的任何修改,都会在清理缓存时同步到数据库中。如下所示:
Customer customer=new Customer(“zx”,27,images);
tx=session.beginTransaction();
session.save(customer);
customer=(Customer)session.load(Customer.class,”1”);
customer.setAge(28);
tx.commit();
这时我们并没有显示调用session.update()方法来保存更新,但是对实体对象的修改还是会同步更新到数据库中,因为此时customer对象通过save方法保存进数据库后,已经是持久化对象了,然后通过load方法再次加载它,它仍然是持久化对象,所以它还处于Hibernate缓存的管理之中,这时当执行tx.commit()方法时,Hibernate会自动清理缓存,并且自动将持久化对象的属性变化同步到到数据库中。
C:游离对象: 游离状态---detached
当一个持久化对象,脱离开Hibernate的缓存管理后,它就处于游离状态,游离对象和自由对象的最大区别在于,游离对象在数据库中可能还存在一条与它对应的记录,只是现在这个游离对象脱离了Hibernate的缓存管理,而自由对象不会在数据库中出现与它对应的数据记录。如下所示:
Customer customer=new Customer(“zx”,27,images);
tx=session.beginTransaction();
session.save(customer);
customer=(Customer)session.load(Customer.class,”1”);
customer.setAge(28);
tx.commit();
session.close();
当session关闭后,customer对象就不处于Hibernate的缓存管理之中了,但是此时在数据库中还存在一条与customer对象对应的数据记录,所以此时customer对象处于游离态。
D:三种对象状态之间的转化:
这三种对象状态,是可以相互转化的,一个自由对象可以通过session.save()方法或者session.saveorupdate()方法变成持久化对象,一个持久化对象可以通过session.flush()或者session.evict()方法,移出Hibernate缓存从而转化为游离对象,一个游离对象可以通过再次加载或者调用session.update()方法,再次恢复为持久化对象,也可以通过调用session.delete()方法变成自由对象,并且删除数据库中对应的数据记录。
示例程序:
Configuration cfg = new Configuration();
SessionFactory sf=cfg.configure().buildSessionFactory();
Customer customer=new Customer(“zx”,27,images);//customer对象处于自由状态
Session session=sf.openSession();
Transaction tx=session.beginTransaction();
session.save(customer);//保存后customer对象处于持久化状态
session.flush();//清空缓存后customer对象处于游离状态
tx.commit();
session.close();
Session session2=sf.openSession();
Transaction tx2=session2.beginTransaction();
session2.update(customer);//通过调用update()方法将游离状态的customer对象,再次转化成持久化状态
session2.delete(customer);//调用delete()方法后,当清空缓存时,会将customer对象移出缓存,同时会在数据库中生成delete事务,来删除customer对象对应的数据记录
tx.commit();
session.close();
2.何谓Hibernate的N+1问题,如何解决?
Hibernate n+1问题
默认情况下,query.iterate查询时候,有可以能出现N+1问题
具体来说当你查询时首先hibernate会发出一天查询所有主键的sql语句,然后跟新缓存。N就是指首先hiberante会到缓存中查询,如果缓存中不存在与之匹配的数据,再会发出sql查询。
主要的原因是:默认情况下iterate利用缓存数据来查询,当缓存为空会多查询一次,把ID加进来。
在Session的缓存中存放的是相互关联的对象图。默认情况下,当Hibernate从数据库中加载Customer对象时,会同时加载所有关联的 Order对象。以Customer和Order类为例,假定ORDERS表的CUSTOMER_ID外键允许为null
以下Session的find()方法用于到数据库中检索所有的Customer对象:
List customerLists=session.find("from Customer as c");
运行以上find()方法时,Hibernate将先查询CUSTOMERS表中所有的记录,然后根据每条记录的ID,到ORDERS表中查询有参照关系的记录,Hibernate将依次执行以下select语句:
select * from CUSTOMERS;
select * from ORDERS where CUSTOMER_ID=1;
select * from ORDERS where CUSTOMER_ID=2;
select * from ORDERS where CUSTOMER_ID=3;
select * from ORDERS where CUSTOMER_ID=4;
通过以上5条select语句,Hibernate最后加载了4个Customer对象和5个Order对象,在内存中形成了一幅关联的对象图.
Hibernate在检索与Customer关联的Order对象时,使用了默认的立即检索策略。这种检索策略存在两大不足:
(1) select语句的数目太多,需要频繁的访问数据库,会影响检索性能。如果需要查询n个Customer对象,那么必须执行n+1次select查询语句。这就是经典的n+1次select查询问题。这种检索策略没有利用SQL的连接查询功能,例如以上5条select语句完全可以通过以下1条 select语句来完成:
select * from CUSTOMERS left outer join ORDERS
on CUSTOMERS.ID=ORDERS.CUSTOMER_ID
以上select语句使用了SQL的左外连接查询功能,能够在一条select语句中查询出CUSTOMERS表的所有记录,以及匹配的ORDERS表的记录。
(2)在应用逻辑只需要访问Customer对象,而不需要访问Order对象的场合,加载Order对象完全是多余的操作,这些多余的Order对象白白浪费了许多内存空间。
为了解决以上问题,Hibernate提供了其他两种检索策略:延迟检索策略和迫切左外连接检索策略。延迟检索策略能避免多余加载应用程序不需要访问的关联对象,迫切左外连接检索策略则充分利用了SQL的外连接查询功能,能够减少select语句的数目。
对数据库访问还是必须考虑性能问题的, 在设定了1 对多这种关系之后, 查询就会出现传说中的n +1 问题。
1 )1 对多,在1 方,查找得到了n 个对象, 那么又需要将n 个对象关联的集合取出,于是本来的一条sql查询变成了n +1 条
2)多对1 ,在多方,查询得到了m个对象,那么也会将m个对象对应的1 方的对象取出, 也变成了m+1
怎么解决n +1 问题?
1 )lazy=true, hibernate3开始已经默认是lazy=true了;lazy=true时不会立刻查询关联对象,只有当需要关联对象(访问其属性,非id字段)时才会发生查询动作。
2)二级缓存, 在对象更新,删除,添加相对于查询要少得多时, 二级缓存的应用将不怕n +1 问题,因为即使第一次查询很慢,之后直接缓存命中也是很快的。
不同解决方法,不同的思路,第二条却刚好又利用了n +1 。
3) 当然你也可以设定fetch=join(annotation : @ManyToOne() @Fetch(FetchMode.JOIN))
3.Hibernate延迟加载的机制是什么,如何工作?
4.Hibernate级联保存要如何做?
5.Hibernate的二级缓存和一级缓存有什么区别?
6.OpenSessionInViewFilter作用及配置
7.Hibernate中的Inverse和cascade属性配置
8.load()和get()的区别
9.hibernate读缓存
分享到:
相关推荐
根据给定文件的信息,我们可以总结出以下几个主要的知识点: ### 1. Struts2 的拦截器(Interceptor)机制 在Struts2框架中,拦截器是处理请求的关键组件之一,可以用于实现诸如权限控制、日志记录等功能。下面...
面试中可能会问到以下几个关键点: 1. **Action和ActionForm**:Action是处理用户请求的核心组件,ActionForm则用于封装表单数据,通常对应于业务逻辑层的实体对象。 2. **配置文件**:Struts的配置主要在struts-...
它主要通过以下几个方面来支持事务: - **TransactionDefinition**: 定义事务的属性,包括隔离级别、传播行为等。 - **TransactionStatus**: 表示当前事务的状态,如是否已提交、是否只读等。 - **...
Java面试通常会涉及到以下几个关键领域: 1. **基础知识**:包括Java的版本历史、基本语法、数据类型、运算符、流程控制等。面试官可能会询问如"Java有哪些访问修饰符?"或"解释一下多态性是什么?"等问题。 2. **...
创建了几个String Object? 第十,(11.5)等於多少? (-11.5)等於多少? 第十一,short s1 = 1; s1 = s1 1;有什么错? short s1 = 1; s1 = 1;有什么错? 面试题都是很变态的,要做好受虐的准备。 第十二,...
面试题集通常涵盖了以下几个方面: 1. **基础知识**:这部分可能包括Java语言的基本语法,如数据类型、变量、运算符、流程控制语句(如if、for、while)等。面试官可能会询问关于类、对象、封装、继承、多态等面向...
Java面试通常会涉及以下几个核心领域: 1. **基础知识**:面试官可能会询问Java的基础语法,如面向对象编程(OOP)概念,类、对象、封装、继承、多态,以及接口与抽象类的区别。此外,异常处理、垃圾回收机制、内存...
在Java的经典面试题中,我们可以看到以下几个重要的知识点: 1. **Java基础**:这部分通常涉及到变量、数据类型、流程控制、异常处理、多线程、集合框架等内容。比如,`equals()` 和 `==` 的区别是面试常考问题,`...
持久层设计是另一个面试常问的话题。持久层是系统中处理数据持久化的部分,它的目标包括数据存储逻辑的抽象、数据访问实现的分离、资源管理以及面向对象的数据操作。常见的Java持久层框架有Hibernate、MyBatis、...
在Java编程语言中,有以下几个重要的知识点: 1. **基础语法**:包括变量、数据类型、运算符、控制结构(如if语句、switch、for、while循环)等,这些都是编程的基础,也是面试中必问的内容。 2. **类与对象**:...
10. **框架与库**:Spring框架、MyBatis、Hibernate等主流Java开发框架的使用和原理也是面试中常问的问题。了解这些框架如何工作,能够显示你的实战经验。 11. **数据库**:SQL查询语言、事务处理、索引优化、JOIN...
5. **J2EE**:Java企业级应用开发的框架,可能包含Servlet、JSP、JDBC、EJB、Spring、Hibernate等相关技术的问题。 6. **ASP.NET** 和 **JSP**:这两者是Web开发的常用技术,涉及服务器端脚本、网页交互、数据库...
10. **数据库知识**:SQL查询、事务管理、索引优化等数据库基础和进阶知识也是面试中常问的内容。 通过《刘晓涛J2EE教程之Java面试题分析》的学习,不仅可以系统地复习Java核心知识点,还能了解到面试中可能出现的...
│ 164个完整Java代码.zip │ J2EE综合--Struts常见错误的全面汇总.txt │ java程序员面试资料.zip │ JAVA笔试题(上海释锐).pdf │ MIME简介.txt │ SCJP试题详解.pdf │ SQL面试题_心灵深处.htm │ Struts+...
3. **异常处理**:理解何时抛出异常,如何捕获和处理异常,以及finally块的作用,这些都是面试中常问的问题。 4. **多线程**:Java提供了强大的多线程支持,面试中可能会涉及线程的创建、同步机制(如synchronized...
│ 164个完整Java代码.zip │ J2EE综合--Struts常见错误的全面汇总.txt │ java程序员面试资料.zip │ JAVA笔试题(上海释锐).pdf │ MIME简介.txt │ SCJP试题详解.pdf │ SQL面试题_心灵深处.htm │ Struts+...
25、说出几个你遇到过的异常 26、说一下spring有什么好处?? 27、linux杀死进程的方式: 28、linux中查看当前线程的方式: 29、说出jdbc的具体实现步骤: 30、 你知道事务吗,说一下事务级别: 31、. js...
J2EE的核心概念包括以下几个方面: 1. **Servlet与JSP**:Servlet是Java编写的小型服务器端程序,用于扩展服务器的功能。JSP(JavaServer Pages)则是一种动态网页技术,将Java代码嵌入HTML中,实现了业务逻辑与...
│ 164个完整Java代码.zip │ J2EE综合--Struts常见错误的全面汇总.txt │ java程序员面试资料.zip │ JAVA笔试题(上海释锐).pdf │ MIME简介.txt │ SCJP试题详解.pdf │ SQL面试题_心灵深处.htm │ Struts+...
│ 164个完整Java代码.zip │ J2EE综合--Struts常见错误的全面汇总.txt │ java程序员面试资料.zip │ JAVA笔试题(上海释锐).pdf │ MIME简介.txt │ SCJP试题详解.pdf │ SQL面试题_心灵深处.htm │ Struts+...