Hibernate相关问题

来源:互联网 发布:js base64转换为pdf 编辑:程序博客网 时间:2024/04/29 09:36

Hibernate相关问题

1.Hibernate工作原理:

1.通过Configuration().configure();

//读取并解析hibernate.cfg.xml配置文件

2.hibernate.cfg.xml中的

<mapping resource="com/xx/User.hbm.xml"/>//读取并解析映射信息

3.通过config.buildSessionFactory();//创建SessionFactory

4.sessionFactory.openSession();//打开Sesssion

5.session.beginTransaction();//创建事务Transation

6.persistent operate持久化操作

7.session.getTransaction().commit();//提交事务

8.关闭Session

9.关闭SesstionFactory

 

2.为什么要用Hibernate?

1. JDBC访问数据库的代码做了封装,大大简化了数据访问层繁琐的重复性代码。 

2. Hibernate是一个基于JDBC的主流持久化框架,是一个优秀的ORM实现。他很大程度的简化DAO层的编码工作 

3. hibernate使用Java反射机制,而不是字节码增强程序来实现透明性。

4. hibernate的性能非常好,因为它是个轻量级框架。映射的灵活性很出色。它支持各种关系数据库,从一对一到多对多的各种复杂关系。 

3. Hibernate是如何延迟加载?

1. Hibernate2延迟加载实现:a)实体对象 

                                   b)集合(Collection

    2. Hibernate3 提供了属性的延迟加载功能 

Hibernate在查询数据的时候,数据并没有存在与内存中,当程序真正对数据的操作时,对象才存在与内存中,就实现了延迟加载,他节省了服务器的内存开销,从而提高了服务器的性能。

 

4Hibernate中怎样实现类之间的关系?(如:一对多、多对多的关系)

     类与类之间的关系主要体现在表与表之间的关系进行操作,它们都市对对象进行操作,我们程序中把所有的表与类都映射在一起,它们通过配置文件中的many-to-oneone-to-manymany-to-many

 

5. 说下Hibernate的缓存机制

1. 内部缓存存在Hibernate中又叫一级缓存,属于应用事物级缓存

2. 二级缓存:

a) 应用及缓存

b) 分布式缓存

条件:数据不会被第三方修改、数据大小在可接受范围、数据更新频率低、同一数据被系统频繁使用、非 关键数据

c) 第三方缓存的实现

一级缓存:session级的缓存也叫事务级的缓存,只缓存实体,生命周期和session一致。不能对其进行管理。不用显示的调用。 

二级缓存:sessionFactory缓存,也叫进程级的缓存,使用第3方插件实现的,也值缓存实体,生命周期和sessionFactory一致,可以进行管理。

首先配置第3放插件,我们用的是EHCache,在hibernate.cfg.xml文件中加入

<property name="hibernate.cache.user_second_level_cache">true</property>

在映射中也要显示的调用,<cache usage="read-only"/>

二级缓存之查询缓存:对普通属性进行缓存。如果关联的表发生了修改,那么查询缓存的生命周期也结束了。

在程序中必须手动启用查询缓存:query.setCacheable(true);

6. Hibernate的查询方式

SqlCriteria,object comptosition

Hql

1、 属性查询

2、 参数查询、命名参数查询

3、 关联查询

4、 分页查询

5、 统计函数

 

7. 如何优化Hibernate

1.使用双向一对多关联,不使用单向一对多

2.灵活使用单向一对多关联

3.不用一对一,用多对一取代

4.配置对象缓存,不使用集合缓存

5.一对多集合使用Bag,多对多集合使用Set

6. 继承类使用显式多态

7. 表字段要少,表关联不要怕多,有二级缓存撑腰

 

8.Hibernate有哪几种查询数据的方式

       (1)导航对象图查询

      (2)OID查询

      (3)HQL

      (4)QBC

      (5)本地SQL

9.Hibernateload()get()的区别?

load加载方法:

Java代码

Users user = (Users)session.load(Users.class, userId);    

Users user = (Users)session.load(Users.class, userId);

get加载方法:

Java代码

Users user = (Users)session.get(Users.class, userId);  

Users user = (Users)session.get(Users.class, userId);

两加载方法区别:

区别1:如果数据库中,没有userId的对象。如果通过get方法加载,则返回的是一个null;如果通过load加载,则返回一个代理对象,如果后面代码如果调用user对象的某个属性(比如user.getPassword())会抛出异常:org.hibernate.ObjectNotFoundException

区别2load支持延迟加载,get不支持延迟加载。

也就是说:

Java代码

Users user = (Users)session.load(Users.class, userId);  

Users user = (Users)session.load(Users.class, userId);

这句代码不会去执行数据库查询,只有用到user时才会去执行数据库查询。

而:

Java代码

Users user = (Users)session.get(Users.class, userId);  

Users user = (Users)session.get(Users.class, userId);

则立即去执行数据库查询。 所以Users user = (Users)session.load(Users.class, userId);不会执行任何sql

注意:

Java代码

Users user = (Users)session.load(Users.class, userId);    

System.out.println(user.getId());  

Users user = (Users)session.load(Users.class, userId);

System.out.println(user.getId());

上面这2句代码,不会去执行数据库操作。因为load后会在hibernate的一级缓存里存放一个map对象,该mapkey就是userId的值,但是当你getId()时,它会去一级缓存里拿mapkey值,而不去执行数据库查询。所以不会报任何错。不会执行任何数据库操作。

10.谈谈你对hibernate的理解?

Hibernate是一个开放源代码的对象关系映射框架,它对JDBC进行了非常轻量级的对象封装,使得Java程序员可以随心所欲的使用对象编程思维来操纵数据库。 Hibernate可以应用在任何使用JDBC的场合,既可以在Java的客户端程序使用,也可以在Servlet/JSPWeb应用中使用,最具革命意义的是,Hibernate可以在应用EJBJ2EE架构中取代CMP,完成数据持久化的重任。

11.hibernatedialectlazyinversecascade属性的用途?

dialect hibernate所使用的方言

lazy 则表示检索是否延迟 true表示打开lazy则延迟检索,false表示关闭lazy直接检索

inverse 常用于一对多双向关联关系中 设置为true 为控制反转 交给另一方去添加数据

cascade 表示级联,一般有all所有情况下级联,none都不级联,sava-update在保存和修改时级联,delete在删除时级联

12.谈谈你对hibernate数据加载方式的认识及使用?

1即时加载(Immediate Loading) 

2当实体加载完成后,立即加载其关联数据 

3延迟加载(Lazy Loading) 

4实体加载时,其关联数据并非马上获取,而是当关联数据第一次被访问时再进行读取

5预先加载(Eager Loading),预先加载时,实体及其关联对象同时读取,这与即时加载类似,不过实体及其关联数据是通过一条SQL语句(基于外连接[outer join])同时读取

6批量加载(Batch Loading),对于即时加载与延迟加载,可以采用批量加载方式进行性能上的优化 

13.描述hibernate中对象的状态及状态间转换的条件?

Hibernate的对象有3种状态,分别为:

瞬时态(Transient)、持久态(Persistent)、脱管态(Detached)

瞬时态 -new命令开辟内存空间的java对象,瞬时对象在内存孤立存在,它是携带信息的载体,不和数据库的数据有任何关联关系,在Hibernate中,可通过sessionsave()saveOrUpdate()方法将瞬时对象与数据库相关联,并将数据对应的插入数据库中,此时该瞬时对象转变成持久化对象。 

持久态  处于该状态的对象在数据库中具有对应的记录,并拥有一个持久化标识。如果是用hibernatedelete()方法,对应的持久对象就变成瞬时对象,因数据库中的对应数据已被删除,该对象不再与数据库的记录关联。 当一个session执行close()clear()evict()之后,持久对象变成脱管对象,此时持久对象会变成脱管对象,此时该对象虽然具有数据库识别值,但它已不在HIbernate持久层的管理之下。 

游离态 (1) 当通过get load方法得到的po对象它们都处于persistent,但如果执行delete(po)(但不能执行事务),po状态就处于 detached, (表示和session脱离关联),delete而变成游离态可以通过savesaveOrUpdate()变成持久态 

(2)当把session关闭时,session缓存中的persistentpo对象也变成detached 因关闭session而变成游离态的可以通过locksaveupdate变成持久态 

持久态 实例可以通过调用 delete()变成脱管状态 。 通过get()load()方法得到的实例都是持久化状态的。 

脱管状态的实例可以通过调用lock()或者replicate()进行持久化。

原创粉丝点击