15.3. 关联(Association)与连接(Join)

优质
小牛编辑
132浏览
2023-12-01

我们也可以为相关联的实体甚至是对一个集合中的全部元素指定一个别名,这时要使用关键字 join

from Cat as cat
    inner join cat.mate as mate
    left outer join cat.kittens as kitten
from Cat as cat left join cat.mate.kittens as kittens
from Formula form full join form.parameter param

受支持的连接类型是从 ANSI SQL 中借鉴来的:

  • inner join

  • left outer join

  • right outer join

  • full join(全连接,并不常用)

语句 inner joinleft outer join 以及 right outer join 可以简写。

from Cat as cat
    join cat.mate as mate
    left join cat.kittens as kitten

通过 HQL 的 with 关键字,你可以提供额外的 join 条件。

from Cat as cat
    left join cat.kittens as kitten
        with kitten.bodyWeight 
> 10.0

A "fetch" join allows associations or collections of values to be initialized along with their parent objects using a single select. This is particularly useful in the case of a collection. It effectively overrides the outer join and lazy declarations of the mapping file for associations and collections. See 第 20.1 节 “抓取策略(Fetching strategies)” for more information.

from Cat as cat
    inner join fetch cat.mate
    left join fetch cat.kittens

一个 fetch 连接通常不需要被指定别名,因为相关联的对象不应当被用在 where 子句(或其它任何子句)中。同时,相关联的对象并不在查询的结果中直接返回,但可以通过他们的父对象来访问到他们。

from Cat as cat
    inner join fetch cat.mate
    left join fetch cat.kittens child
    left join fetch child.kittens

假若使用 iterate() 来调用查询,请注意 fetch 构造是不能使用的(scroll() 可以使用)。fetch 也不应该与 setMaxResults()setFirstResult() 共用,这是因为这些操作是基于结果集的,而在预先抓取集合类时可能包含重复的数据,也就是说无法预先知道精确的行数。fetch 还不能与独立的 with 条件一起使用。通过在一次查询中 fetch 多个集合,可以制造出笛卡尔积,因此请多加注意。对 bag 映射来说,同时 join fetch 多个集合角色可能在某些情况下给出并非预期的结果,也请小心。最后注意,使用 full join fetchright join fetch 是没有意义的。

如果你使用属性级别的延迟获取(lazy fetching)(这是通过重新编写字节码实现的),可以使用 fetch all properties 来强制 Hibernate 立即取得那些原本需要延迟加载的属性(在第一个查询中)。

from Document fetch all properties order by name
from Document doc fetch all properties where lower(doc.name) like '%cats%'