|
【郑州校区】检索策略(抓取策略)
1.1. 延迟加载延迟加载 是hibernate为提高程序执行的效率而提供的一种机制,即只有真正使用该对象的数据时才会创建。 load方法采用的策略延迟加载. get方法采用的策略立即加载。 检索策略分为两种: 1. 类级别检索 2. 关联级别检索 1.2. 类级别检索类级别检索是通过session直接检索某一类对应的数据,例如 Customer c=session.load(Customer.class,1) Session.createQuery(“from Order”) 类级别检索策略分为立即检索与延迟检索,默认是延迟检索,类级别的检索策略可以通过<class>元素的lazy属性来设置 ,默认值是true 在hbm配置文件中设置 在类中使用注解 如果将lazy设置为false,代表类级别检索也使用立即检索。这时load与get就一样,都是立即检索。 如果对一个延迟代理对象进行初始化? 1.3. 关联级别检索 查询到某个对象,获得其关联的对象或属性,这种称为关联级别检索,例如 c.getOrders().size() c.getName() 对于关联级别检索我们就要研究其检索策略(抓取策略) 1.4. 检索策略(抓取策略)延迟加载延迟加载 是hibernate为提高程序执行的效率而提供的一种机制,即只有真正使用该对象的数据时才会创建。 load方法采用的策略延迟加载. get方法采用的策略立即加载。 检索策略分为两种: 3. 类级别检索 4. 关联级别检索 类级别检索类级别检索是通过session直接检索某一类对应的数据,例如 Customer c=session.load(Customer.class,1) Session.createQuery(“from Order”) 类级别检索策略分为立即检索与延迟检索,默认是延迟检索,类级别的检索策略可以通过<class>元素的lazy属性来设置 ,默认值是true 在hbm配置文件中设置 在类中使用注解 如果将lazy设置为false,代表类级别检索也使用立即检索。这时load与get就一样,都是立即检索。 如果对一个延迟代理对象进行初始化? 关联级别检索 查询到某个对象,获得其关联的对象或属性,这种称为关联级别检索,例如 c.getOrders().size() c.getName() 对于关联级别检索我们就要研究其检索策略(抓取策略) 检索策略(抓取策略)抓取策略介绍 指的是查找到某个对象后,通过这个对象去查询关联对象的信息时的一种策略。 一对一 <one-to-one> 一对多(多对一) <set>下有<one-to-many> <many-to-one> 多对多 <set>下有<many-to- many> 我们主要是在<set>与<many-to-one>或<one-to-one>上设置fetch lazy 例如:查询一个客户,要关联查询它的订单 客户是一的一方,在客户中有set集合来描述其订单,在配置中我们是使用 <set> <one-to-many> </set>.. 可以在set标签上设置两个属性 fetch lazy Fetch主要描述的是SQL语句的格式(例如是多条,子查询,多表联查 Lazy 控制SQL语句何时发送 例如:在查询一个订单时,要查询客户信息 <many-to-one> 或<one-to-one> 也可以设置fetch lazy Fetch主要描述的是SQL语句的格式(例如是多条,子查询,多表联查 Lazy 控制SQL语句何时发送 总结: 讲解抓取策略 在两方面设置 <set fetch=”” lazy=””> <many-to-one fetch=”” lazy=””> <one-to-one> 注解配置抓取策略问题:如何使用注解来设置 在<setse>设置的fetch与lazy可以使用下面注解来描述 file:///C:\Users\ADMINI~1\AppData\Local\Temp\ksohtml\wps89F6.tmp.jpg 在<many-to-one>或<one-to-one>上如何设置 fetch与lazy set上的fetch与lazyset上的fetch与lazy它主要是用于设置关联的集合信息的抓取策略。 Fetch可取值有: 1. SELECT 多条简单的sql (默认值) 2. JOIN 采用迫切左外连接 3. SUBSELECT 将生成子查询的SQL lazy可取值有: 1. TURE 延迟检索 (默认值) 2. FALSE 立即检索 3. EXTRA 加强延迟检索(及其懒惰) 第一种组合 会首先查询客户信息,当需要订单信息时,才会关联查询订单信息。 第二种组合s
当查询客户信息时,就会将订单信息也查询,也就是说订单信息没有进行延迟。 第三种组合当查询客户信息时,不会查询订单信息,当需要订单的个数时,也不会查询订单信息, 只会通过count来统计订单个数。 当我们使用size(),contains()或isEmpty()方法时不会查询订单信息。 第四种组合如果fetch选择的是join方案,那么lazy它会失效。 生成SQl将采用的是迫切左外连接(left outer join fetch) 会立即查询。 第五种组合会生成子查询,但是我们在查询订单时采用的是延迟加载。 第六种组合会生成子查询,在查询客户信息时,就会将订单信息也查询出来 第七种组合在查询订单时,只会根据情况来确定是否要订单信息,如果不需要,例如我们 程序中size操作,那么就会发出select count(*) from Order where c_customer_id=? One的一言fetch与lazy<set fetch lazy>它主要是设置在获取到一的一方时,如果去查询多的一方。 在<many-to-one>或<one-to-one>如果去查询对方。 对于程序 就是在多的一方如何查询一的主方信息 例如:获取到一个订单对象,要查询客户信息。 Fetch可取值: select 默认值,代表发送一条或多条简单的select语句 join 发送一条迫切左外连接 lazy可取值 false 不采用延迟加载 proxy 默认值 是否采用延迟,需要另一方的类级别延迟策略来决定 no-proxy 不用研究 第一种组合注意:Customer的类级别延迟策略 当我们执行时,会首先发送一条sql只查询订单信息,客户信息会延迟,只有真正需要客户信息时,才会发送sql来查询客户信息. 第二种组合注意:Customer的类级别延迟策略 当查询订单时,就会将客户信息也查询到,原因是Customer它的类级别延迟为false,也就是立即查询。 第三种组合当查询订单时,不会对客户信息进行延迟,立即查询客户信息 第四种组合如果fetch值为join,那么lazy失效。 会发送一条迫切左外连接来查询,也就立即查询。 1.5. 批量抓取我们在查询多个对象的关联对象时,可以采用批量抓取方式来对程序进行优化. 要想实现批量抓取: 可以在配置文件中 batch-size属性来设置 可以使用注解 @BatchSize(size=4) 可以采用批量抓取来解决N+1问题. 查询客户,查询订单可以在客户配置文件中配置batch-size,是在<set>标签上 查询订单,查询客户订单与客户,客户它是一个主表,订单是一个从表。 在设置批量抓取时都是在主表中设置 在配置文件中在主表的<calss>标签上设置batch-size 在注解使用中 注意:无论是根据哪一方来查询别一方,在进行批量抓取时,都是在父方来设置 , 如果是要查询子信息,那么我们是在<set>上来设置batch-size,如果是从子方来查询父方, 也是在父方设置在<class>设置batch-size.
父与子区分: 有外键的表是子(从关联方就是父(主)表 传智播客·黑马程序员郑州校区地址 河南省郑州市 高新区长椿路11号大学科技园(西区)东门8号楼三层 联系电话 0371-56061160/61/62 来校路线 地铁一号线梧桐街站A口出
|