使用 Hibernate 的 Criteria API,我想选择具有给定列的最大值的表中的记录。
我尝试使用 Projections,创建别名来获取 max(colunName)
的值,然后在restrictions.eq()
中使用它,但是它一直告诉我"不合法的数字"。
使用Hibernate的正确方法是什么?
使用 Hibernate 的 Criteria API,我想选择具有给定列的最大值的表中的记录。
我尝试使用 Projections,创建别名来获取 max(colunName)
的值,然后在restrictions.eq()
中使用它,但是它一直告诉我"不合法的数字"。
使用Hibernate的正确方法是什么?
您可以使用DetachedCriteria
来表示子查询,就像这样:
DetachedCriteria maxId = DetachedCriteria.forClass(Foo.class)
.setProjection( Projections.max("id") );
session.createCriteria(Foo.class)
.add( Property.forName("id").eq(maxId) )
.list();
我发现同时使用addOrder
和setMaxResults
对我有用。
Criteria c = session.createCriteria(Thingy.class);
c.addOrder(Order.desc("id"));
c.setMaxResults(1);
return (Thingy)c.uniqueResult();
使用MySQL方言,这将生成一个SQL预处理语句,类似于以下内容(省略了一些字段):
select this_.id ... from Thingy this_ order by this_.id desc limit ?
我不确定这个解决方案是否对除MySQL以外的方言有效。
使用
addOrder(Order.desc("id"))
并且只获取第一个结果 :)
HQL:
from Person where person.id = (select max(id) from Person)
未经测试。您的数据库需要理解where子句中的子查询。
如果/如何使用criteria api表达这样的子查询太麻烦了。当然,您可以执行两个查询:首先获取最大id,然后获取该id对应的实体。
Date maxDateFromDB = null;
Session session = (Session) entityManager.getDelegate();
//Register is and Entity and assume maxDateFromDB is a column.
//Status is another entity with Enum Applied.
//Code is the Parameter for One to One Relation between Register and Profile entity.
Criteria criteria = session.createCriteria(Register.class).setProjection(Projections.max("maxDateFromDB") )
.add(Restrictions.eq("status.id", Status.Name.APPLIED.instance().getId()));
if(code != null && code > 0) {
criteria.add(Restrictions.eq("profile.id", code));
}
List<Date> list = criteria.list();
if(!CollectionUtils.isEmpty(list)){
maxDateFromDB = list.get(0);
}
完全使用Detached Criteria来完成它(因为我喜欢在没有session的情况下构建Detached Criteria)
DetachedCriteria maxQuery = DetachedCriteria.forClass(Foo.class)
.setProjection( Projections.max("id") );
DetachedCriteria recordQuery = DetachedCriteria.forClass(Foo.class)
.add(Property.forName("id").eq(maxId) );
DetachedCriteria criteria = DetachedCriteria.forClass(Foo.class).setProjection(Projections.max("id"));
Foo fooObj =(Foo) criteria.getExecutableCriteria(getCurrentSession()).list().get(0);
关于 Hibernate 中的 max()
函数:
criteria.setProjection(Projections.max("e.encounterId"));