在条件 api 中转换表达式的结果
Casting expression's result in criteria api
我有这个代码:
CriteriaBuilder criteriaBuilder = em.getCriteriaBuilder();
CriteriaQuery<Integer> criteriaQuery = criteriaBuilder.createQuery(Integer.class);
Root<Teacher> c = criteriaQuery.from(Teacher.class);
Expression s = criteriaBuilder.locate(c.<String>get("fam"), "-").as(Integer.class);
Integer lastIndex = Integer.valueOf(s.toString());
criteriaQuery.select(criteriaBuilder.max(criteriaBuilder.substring(c.<String>get("fam"), 1, lastIndex-1).as(Integer.class)));
Integer aaa = em.createQuery(criteriaQuery).getSingleResult();
s
变量给我整数。我想将它用作 substring
函数的参数。我怎样才能做到这一点?这个方法不行。
您可以使用以下解决方案:
CriteriaBuilder builder = session.getCriteriaBuilder();
CriteriaQuery<Integer> criteria = builder.createQuery(Integer.class);
Root<Teacher> root = criteria.from(Teacher.class);
Expression<Integer> exp = builder.locate(root.get("fam"), "-");
Expression<Integer> one = builder.literal(1);
Expression<String> numberAsString = builder.substring(
root.get("fam"),
one,
builder.diff(exp, one)
);
Expression<Integer> toNumber = builder.function(
"TO_NUMBER",
Integer.class,
numberAsString
);
criteria.select(
builder.max(toNumber)
);
Integer result = session.createQuery( criteria ).getSingleResult();
在这段代码中,我假设您使用的是 oracle 数据库。 TO_NUMBER 函数是 oracle 特定函数,它将第一个参数转换为 NUMBER
数据类型的值。我想类似的功能应该存在于所有数据库中。
另请注意,由于 HHH-11938,TO_NUMBER
函数应在您的休眠方言中声明。在我的例子中,这个函数没有在 org.hibernate.dialect.Oracle12cDialect
中声明。所以,我通过以下方式扩展了这个方言:
import org.hibernate.dialect.Oracle12cDialect;
import org.hibernate.dialect.function.StandardSQLFunction;
import org.hibernate.type.StandardBasicTypes;
public class MyOracleDialect extends Oracle12cDialect
{
public MyOracleDialect()
{
super();
registerFunction("to_number", new StandardSQLFunction("to_number", StandardBasicTypes.INTEGER) );
}
}
然后在休眠配置中使用它hibernate.cfg.xml
<!DOCTYPE hibernate-configuration SYSTEM "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.dialect">com.sternkn.hibernate.MyOracleDialect</property>
...
</session-factory>
</hibernate-configuration>
我有这个代码:
CriteriaBuilder criteriaBuilder = em.getCriteriaBuilder();
CriteriaQuery<Integer> criteriaQuery = criteriaBuilder.createQuery(Integer.class);
Root<Teacher> c = criteriaQuery.from(Teacher.class);
Expression s = criteriaBuilder.locate(c.<String>get("fam"), "-").as(Integer.class);
Integer lastIndex = Integer.valueOf(s.toString());
criteriaQuery.select(criteriaBuilder.max(criteriaBuilder.substring(c.<String>get("fam"), 1, lastIndex-1).as(Integer.class)));
Integer aaa = em.createQuery(criteriaQuery).getSingleResult();
s
变量给我整数。我想将它用作 substring
函数的参数。我怎样才能做到这一点?这个方法不行。
您可以使用以下解决方案:
CriteriaBuilder builder = session.getCriteriaBuilder();
CriteriaQuery<Integer> criteria = builder.createQuery(Integer.class);
Root<Teacher> root = criteria.from(Teacher.class);
Expression<Integer> exp = builder.locate(root.get("fam"), "-");
Expression<Integer> one = builder.literal(1);
Expression<String> numberAsString = builder.substring(
root.get("fam"),
one,
builder.diff(exp, one)
);
Expression<Integer> toNumber = builder.function(
"TO_NUMBER",
Integer.class,
numberAsString
);
criteria.select(
builder.max(toNumber)
);
Integer result = session.createQuery( criteria ).getSingleResult();
在这段代码中,我假设您使用的是 oracle 数据库。 TO_NUMBER 函数是 oracle 特定函数,它将第一个参数转换为 NUMBER
数据类型的值。我想类似的功能应该存在于所有数据库中。
另请注意,由于 HHH-11938,TO_NUMBER
函数应在您的休眠方言中声明。在我的例子中,这个函数没有在 org.hibernate.dialect.Oracle12cDialect
中声明。所以,我通过以下方式扩展了这个方言:
import org.hibernate.dialect.Oracle12cDialect;
import org.hibernate.dialect.function.StandardSQLFunction;
import org.hibernate.type.StandardBasicTypes;
public class MyOracleDialect extends Oracle12cDialect
{
public MyOracleDialect()
{
super();
registerFunction("to_number", new StandardSQLFunction("to_number", StandardBasicTypes.INTEGER) );
}
}
然后在休眠配置中使用它hibernate.cfg.xml
<!DOCTYPE hibernate-configuration SYSTEM "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<property name="hibernate.dialect">com.sternkn.hibernate.MyOracleDialect</property>
...
</session-factory>
</hibernate-configuration>