黑马程序员技术交流社区
标题: 【重庆校区】-【基础框架总结】-【 Hibernate】 [打印本页]
作者: 陈文老师 时间: 2017-11-22 11:07
标题: 【重庆校区】-【基础框架总结】-【 Hibernate】
本帖最后由 陈文老师 于 2017-11-22 11:20 编辑
要毕业了?要找工作啦?开不开心?紧不紧张?回首黑马这半年,感觉自己是不是被自己的努力所感动,然而仔细想想学了很多,马上要出去找工作了却脑子一片空白。重庆JavaEE就业2期龙师兄毕业后在寝室闭关修炼半个月(当然不建议大家这样做,一定要趁着你刚毕业,什么都知道赶紧出去找工作,越到后面越忘得多)个人总结了咱们6个月以来所学的一些基础框架和淘淘项目的一些核心技能点,要复习的,赶紧看看吧!但是答应我,看完后赶紧出去面试哟~~~不要怂,就是干!!!
【基础框架篇】-【Hibernate】
1 Hibernate
1.1 什么是hibernate?
1. Hibernate是一个开源的对象关系映射框架,它对jdbc进行了非常轻量级的对象封装,它将破基于数据库建立映射关系,是一个全自动orm框架,hibernate开源自动生成sql语句,自动执行,使得java程序员开源随心所欲的使用面向对象思维来操作数据库,
2. Hibernate中常用api
a) Configuration,它主要是用于加载hibernate配置
b) SessionFactory,sessionFactory接口负责初始化hibernate,它充当数据存储源的代理,并负责创建session对象,一般情况下一个项目只有一个sessionFactory就够,
c) Session,session接口负责执行被持久化对象的crud操作,但是需要注意session对象时线程不安全的。一般在方法内部使用session,获取session的方法:
A. SessionFactory.openSession();相当于直接通过sessionFactory创建一个新的session,使用完成后需要手动关闭
B. SessionFactory.getCurrentSession(),获取一个与当前线程绑定的session,当我们提交或者事务回滚后会自动关闭。
d) Transaction,主要用于管理事务,它是hibernate的事务接口,对底层的事务进行了封装,其中的事务操作有:
A. Commit事务提交
B. Rollback事务回滚
C. 获取transaction:session.beginTransaction()
D. 程序中没有开启事务也是存在事务的,session的每一个操作就会开启一个事务,默认情况下事务是不自动提交,可以配置自动提交<property name =”hibernate.connection.autocommit”>true</>
e) Query,它作用是让你方便对数据库及持久化对象进行查询,它可以有两种表达方式:
A. Hql
B. Sql
f) SQLQuery,想要执行本地sql,session.createSqlQuery(String sql),使用addEntity()方法来将结果封装到指定的对象中,吴国不封装得到的是一个list<>集合,如果sql中有参数,我们使用setParamerter()方法完成参数传递
g) Criteria,Criteria接口与query接口非常类似,允许创建并执行面向对象的标准化查询,Criteria是一个轻量级的,它不能在session之外使用。通过session.createCriteria()获取criteria。
3. Hibernate持久化对象是那种状态
a) 瞬时态:它一般指我们new出来的对象,它不存在oid,与session无关联,在数据库中无记录,它使用完成后就会被jvm统一回收,它只是用于信息携带
b) 持久态:在session管理范围内,它具有持久化标识oid它的特点,在事务未提交之间一直保持持久太,当它发生 改变时,hibernate时可以检测到的
c) 托管态:它是指持久态对象失去了与session的关联,托管态对象存在oid,在数据库中有可能存在,也有可能不存在。它发生改变,hibernate检测不到。
4. Hibernate的一级缓存(session缓存)
a) 存在的目的是为了减少对数据库的访问
b) ActionQueue是一个行列队列,它主要记录crud操作的相关信息
c) PersistenceContext是持久化上下文,它其实是真正的缓存。
d) 一级缓存的特点:
A. 当我们通过session的save,update,saveOrUpdate进行操作时,如果一级缓存中没有对象,会将这些对象从数据库中查询到,存储在一级缓存中
B. 当我们通过session的load,get,query的list等方法进行操作时,会先判断一级缓存中是否存在,如果没有才会从数据库获取,并且将查询的数据存储到一级缓存中
C. 当调用session的close方法时,session缓存清空
5. Hibernate的二级缓存(sessionFactory级别的缓存)
6. Hibernate关联映射-数据对象三种关系
a) 一对一
A. 唯一外键对应:在任意一方添加外键来描述对应关系
B. 主键对应:一方的主键作为另一方的主键
b) 多对一:建表原则,在多的一方添加外键来描述关联关系
c) 多对多:建表原则,通过一张中间表来描述对应关系
7. 检索策略
a) 延迟加载:是hibernate为提高程序执行的效率而提供的一种机制,即只有真正使用该对象的数据时才会创建
A. Load方法采用的策略延迟加载
B. Get方法采用的策略立即加载
b) 检索策略分为两种
A. 类级别检索
i. 类级别检索是通过session直接检索某一类对应的数据,如:XXX xxx=session.load(xxx.class,1);session.createQuery(“from Order”)
ii. 类级别检索策略分为立即检索和延迟检索,默认是延迟检索,类级别的检索策略可以通过<class>元素的lazy属性来设置,默认为true,即在hbm配置文件中设置:
在类中使用注解@Proxy(lazy=true),如果配置为false时,代表类级别检索页使用立即检索,赭石load和get就一样了。
B. 关联级别检索
i. 查询到某个对象,获得其关联的对象或属性,这种称为关联级别检索,如:xxx.getX().size()
C. 配置文件抓取策略:指的是查询到某个对象后,通过这个对象去查询关联对象的信息时的一种策略。
i. 一对一、一对多、多对多分别在<set>元素下设置他们的属性fetch、lazy。Fetch主要描述的是sql语句的格式(子查询、多表联合查询等),Lazy用于控制语句何时发送。如:<set fetch=”” lazy=””>或者<many-to-onefetch=”” lazy=””>
D. 注解抓取策略
iii. Fetch的取值有,SELECT(多条简单的sql)默认值,JOIN采用迫切左外连接,SUBSELECT将产生子查询的sql
iv. Lazy的取值有:TRUE延迟检索,FALSE立即检索,EXTRA加强延迟检索(及其懒惰)。
E. 批量抓取
i. 可以在配置文件中batch-size属性来设置
ii. 可以使用注解@BatchSize(size=x)
iii. 可以采用批量抓取解决N+1问题
1.2 为什么使用hibernate?
1. Hibernate 对jdbc访问数据库的代码做了封装,大大简化了库访问层繁琐的重复性代码
2. Hibernate是一个基于jdbc的主流持久化框架,是一个优秀的orm实现,它很大程度的简化了dao层编码工作
3. Hql优化
a) 使用参数绑定:使用绑定参数的原因是让数据库一次解析sql,对后续的重复请求可以使用生成号的执行计划,这样节省cpu时间和内存,也避免了sql注入
b) 尽量少全长not:如果where子句包含not关键字,name执行该字段的索引失效
c) 尽量使用where来替换having:having在检索出所有记录后才对结果集进行过滤,这个处理需要一定的开销,而where子句限制记录的数目,能减少这方面的开销
d) 减少对表的查询:在含有子查询的hql中,尽量减少对表的查询,降低开销
e) 使用表的别名:当在hql语句中连接多个表时,使用别名,提高程序阅读性,并把别名前缀与每个列上,这样可以减少解析时间并减少列歧义引起的语法错误
f) 实体的更行与删除:在hibernate3以后支持hql的update和delete操作
1.3 怎么使用hibernate?
1. Hibernate的hbm.xml配置:主要用于描述实体类和数据库表之间的映射关系
a) 位置:加载时需要许实体类在同一个目录下,所以可以将其放在实体类的包中,也可以放在maven管理下的resource目录下与实体类包一直的目录下
b) <hibernate-mapping package=”实体类包名”>:统一声明包名,这样在<class>下就不用写类的全限定名了
c) <class name=”实体类” table=“表名” catalog=“数据库名”>:name属性:类的全名称,table表的名字,catalog数据库名称
d) <id name=”对象主键名” column=“数据表中主键名” ,length=“”“”,type=“类型”><generator class=”生成策略” >,必须存在,
e) <property name=”普通属性名” column=“数据库对应的字段名” length=“长度”>它描述类中属性与表中非主键的映射关系
f) Hbm映射文件编写
A.
B.
C. 级联操作:
D. 双向关联维护:我们发中要配置双向关联配置,通过任意一方来操作对方;在代码中,尽量要进行单项关联,这样可以尽量减少资源浪费;在双向关联中,会存在多余的update语句;使用inverse属性来设置,双向关联时由哪一方来维护表与表之间的关系
inverse为true表示由对方来维护外键,false表示自己来维护外键
E. 级联删除,为了维护数据的完整性
g) hibernate注解开发
A. @Entity声明一个实体
B. @Table来描述与表对应
C. @Id来声明一个逐渐
D. @GenerateValue用它声明一个逐渐生成策略
E. @Column来定义列
F. @Temoral声明时间类型
G. @OneToMany(targetEntity=xxx.class,mappedBy=”yyy”)mappedBy表示由对方来维护外键,
H. @ManyToOne(targetEntity=xxx.class),
I. @JionColumn(name=”xxx”)指定外键列
J. 一下表述以uuid的方式生成主键,表示外键由对方来维护
2. Hibernate的核心配置文件:它主要是hibernate框架所使用的,它主要包含了连接出具库相关信息,hibernate相关配置等
a) 位置:在src下创建一个hibernate.cfg.xml
b) cfg.xml配置
A. <hibernate-configuration>
B. <session-factory>, session工厂
C. <property>,可以用它配置关于数据库的四项,driverClass、url、username、password。也可以用于配操作置数据库的设置,如:显示sql,格式化sql,hibernate的方言等
D. <mapping resource=“映射文件位置”>,用于指定对象关系映射文件的位置
c)
3. Hibernate工作原理
a) 通过configuration().configure():读取并解析,hibernate.cfg.xml配置文件
b) 由hibernate.cfg.xml中的<mapping resource=””>读取解析映射信息
c) 通过config.buildSourceFactory();得到sessionFactory
d) SessionFactroy.openSession()得到session
e) Session.beginTransaction(),开启事务
f) Persistent operate
g) Session.getTransaction().commit()提交事务
4. Hibernate中session管理
a) Session对象的生命周期与本地线程绑定
A. 需要在cfg.xml配置文件中配置<property name=”hibernate.current_session_context_class”>thread</>,获取session时是调用getCurrentSession()方法获取。
b) Session对象的生命周期与jta事务绑定(分布式事务管理)
c) Hibernate委托程序来管理session的生命周期
作者: 雷米 时间: 2017-11-22 15:28
很详细全面,谢谢老师,收藏了
作者: 陈文老师 时间: 2017-11-22 17:15
客气呢~~~~~
作者: 渝鱼鱼 时间: 2017-11-25 10:37
很详细很全面,谢谢老师,收藏了
欢迎光临 黑马程序员技术交流社区 (http://bbs.itheima.com/) |
黑马程序员IT技术论坛 X3.2 |