java 对儿童有限制的 Hibernate 标准
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/7003861/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Hibernate criteria with restrictions on children
提问by jonathan.cone
I have a Hibernate criteria call that I want to execute in one SQL statement. What I'm trying to do is select instances of Parent that have Children with a property in a range of values (SQL IN clause), all while loading the children using an outer join. Here's what I have so far:
我有一个 Hibernate 标准调用,我想在一个 SQL 语句中执行它。我想要做的是选择 Parent 的实例,这些实例具有在一系列值(SQL IN 子句)中具有属性的 Children,同时使用外部联接加载子项。这是我到目前为止所拥有的:
Criteria c = session.createCriteria(Parent.class);
c.createAlias("children", "c", CriteriaSpecification.LEFT_JOIN)
.setFetchMode("c", FetchMode.JOIN)
.add(Restrictions.in("c.property", properties));
c.setResultTransformer(CriteriaSpecification.DISTINCT_ROOT_ENTITY);
return c.list();
Here's some sample data:
以下是一些示例数据:
Parent
Parent ID
A
B
C
Children
Child ID Parent ID property
... A 0
... A 2
... A 7
... B 1
... C 1
... C 2
... C 3
What I want to do is return the parents and ALL their children if one of the children has a property equal to my bind parameter(s). Let's assume properties is an array containing {2}. In this case, the call will return parents A and C but their child collections will contain only element 2. I.e. Parent[Children]:
我想要做的是返回父母和他们所有的孩子,如果其中一个孩子的属性等于我的绑定参数。让我们假设 properties 是一个包含 {2} 的数组。在这种情况下,调用将返回父 A 和 C,但它们的子集合将仅包含元素 2。即 Parent[Children]:
A[2] & C[2]
A[2] & C[2]
What I want is:
我想要的是:
A[0, 2, 7] & C[1, 2 3]
A[0, 2, 7] & C[1, 2 3]
If this is not a bug, it seems to be a broken semantic. I don't see how calling A.getChildren() or C.getChildren() and returning 1 record would ever be considered correct -- this is not a projection. I.e. if I augment the query to use the default select fetch, it returns the proper children collections, albiet with a multitude of queries:
如果这不是一个错误,它似乎是一个破碎的语义。我不明白如何调用 A.getChildren() 或 C.getChildren() 并返回 1 条记录会被认为是正确的——这不是预测。即,如果我增加查询以使用默认选择提取,它会返回正确的子集合,尽管有大量查询:
c.createAlias("children", "c").add(
Restrictions.in("c.property", properties));
Is this a bug? If not, how can I achieve my desired result?
这是一个错误吗?如果没有,我怎样才能达到我想要的结果?
回答by binary
Criteria c = session.createCriteria(Parent.class);
c.createAlias("children", "children");
c.add(Restrictions.in("children.property", properties));
c.setResultTransformer(CriteriaSpecification.DISTINCT_ROOT_ENTITY);
return c.list();
回答by Karthi Murugan
This can be done in work around way.
这可以通过变通的方式来完成。
Criteria c1 = session.createCriteria(Child.class);
c1.add(Restrictions.in("property", properties));
c1.setProjection( Projections.distinct( Projections.property( "parentId" ) ) );
List<Integer> parentIds = c1.list();
Criteria c2 = session.createCriteria(Parent.class);
c2.createAlias("children", "children");
c2.add(Restrictions.in("id", parentIds));
return c2.list();
回答by dfb
getChildren() is just the name of the getter/setter, your query will determine how the objects get populated.
getChildren() 只是 getter/setter 的名称,您的查询将确定对象如何填充。
I'm going to guess here that the first part spits out
我会在这里猜测第一部分吐出来
SELECT * FROM Parent
INNER JOIN Child c ON ...
WHERE c.property in (x,y,z)
which doesn't get you what you want. What'd you'd want to do if you were writing this in raw SQL is this:
这不会让你得到你想要的。如果您使用原始 SQL 编写此代码,您想要做的是:
SELECT * FROM Parent
WHERE ParentID IN (SELECT DISTINCT parentID FROM Child WHERE c.property in (x,y,z))
rearranging your criteria appropriately might do the trick if the last one isn't producing this query. (Could you also post what hibernate is generating for each?)
如果最后一个没有生成此查询,则适当地重新排列您的标准可能会奏效。(您能否也发布每个休眠生成的内容?)
回答by Victor Ionescu
I would start the Criteria with the child class. You'll get a list with all the children, and then you can iterate and get the parent for each children.
我会从儿童班开始标准。您将获得包含所有孩子的列表,然后您可以迭代并获取每个孩子的父母。