Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/393.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么这个Hibernate条件查询失败,并且“没有显式选择,也没有确定隐式选择”?_Java_Hibernate_Hibernate Criteria_Criteriaquery - Fatal编程技术网

Java 为什么这个Hibernate条件查询失败,并且“没有显式选择,也没有确定隐式选择”?

Java 为什么这个Hibernate条件查询失败,并且“没有显式选择,也没有确定隐式选择”?,java,hibernate,hibernate-criteria,criteriaquery,Java,Hibernate,Hibernate Criteria,Criteriaquery,我有一个名为Bucket的实体,我正在尝试构建一个条件查询,以确定是否存在一个存储了Name属性等于Bucket_1的Bucket。所以基本上它是一个exists查询 Bucket类没有什么特别之处,更简单的是: @Entity(name="Bucket") @Table(name = "BUCKETS") public class Bucket implements Serializable { private static final long serialVersionUID =

我有一个名为Bucket的实体,我正在尝试构建一个条件查询,以确定是否存在一个存储了Name属性等于Bucket_1的Bucket。所以基本上它是一个exists查询

Bucket类没有什么特别之处,更简单的是:

@Entity(name="Bucket")
@Table(name = "BUCKETS")
public class Bucket implements Serializable {
    private static final long serialVersionUID = 1L;

    @Column(name = "BUCKET_NAME", length=200)
    private String Name;

        ...
}
对于查询,这是我到目前为止所做的:

CriteriaBuilder criteriaBuilder = em.getCriteriaBuilder();
CriteriaQuery<Boolean> superQuery = criteriaBuilder.createQuery(Boolean.class);

Class<? extends T> scopeClass = Bucket.class;
Root<? extends T> root = superQuery.from(scopeClass);

Path<?> attributePath = root.get("Name");
Predicate pred = criteriaBuilder.equal(attributePath, criteriaBuilder.literal("Bucket_1"));

Subquery<? extends T> subQuery = superQuery.subquery(scopeClass);
subQuery.where(pred);
Predicate where = criteriaBuilder.exists(subQuery);

superQuery = superQuery.select(where);

/* This line fails!! */
TypedQuery<Boolean> typedQuery = em.createQuery(superQuery);

boolean result = typedQuery.getSingleResult();
我做了很多研究,但找不到任何人有相同的错误解释和/或修复

我也试过这样做:

CriteriaBuilder criteriaBuilder = em.getCriteriaBuilder();
CriteriaQuery<Boolean> superQuery = criteriaBuilder.createQuery(Boolean.class);

Class<? extends T> scopeClass = Bucket.class;
superQuery.from(scopeClass);
Subquery<? extends T> subQuery = superQuery.subquery(scopeClass);
Root<? extends T> root = subQuery.from(scopeClass);

Path<?> attributePath = root.get("Name");
Predicate pred = criteriaBuilder.equal(attributePath, criteriaBuilder.literal("Bucket_1"));

Subquery<? extends T> subQuery = superQuery.subquery(scopeClass);
subQuery.where(pred);
Predicate where = criteriaBuilder.exists(subQuery);

superQuery = superQuery.select(where);

/* This line fails!! */
TypedQuery<Boolean> typedQuery = em.createQuery(superQuery);
boolean result = typedQuery.getSingleResult();
我想最难的部分是得到选择1。。。这样,外部查询的结果是布尔值,而不是匹配的实体

我知道这本书很管用,我现在正努力学习如何正确使用它,我相信有一种方法…

你能做到这一点吗

boolean result = (session.createCriteria(Bucket.class)
       .add(Restrictions.eq("Name","Bucket_1"))
       .setProjection(Projections.count("Name"))
       .uniqueResult() > 0);

这个解决方案确实有效,但我想使用exists构造来解决性能问题。我会做无数的记录来检查。exists结构的性能应该更好,因为一旦找到第一个与限制匹配的记录,DBMS就会停止查找记录。使用计数,它必须检查所有数据,然后分离不同的数据,然后才完成查询?类似于Oracle,从存在的双存储中选择1,从name='BUCKET_1'的存储桶中选择*?我会看看我是否有想法并更新答案。我认为分离查询应该可以工作。顺便说一句,按照这个性能逻辑,您可以始终使用setMaxResults1进行查询。您在setMaxResult1上有一个很好的观点,我可能最终会将建议的解决方案与您的建议结合起来。这个查询看起来就像你写的,是的!实际上,它可能会更简单,因为您不需要计数投影。而不是uniqueResult do list,并将其大小与0进行比较。可能需要设置id投影,这样就不必传输所有列。
CriteriaBuilder criteriaBuilder = em.getCriteriaBuilder();

CriteriaQuery<Bucket> query = criteriaBuilder.createQuery(Bucket.class);
Root<Bucket> root = query.from(Bucket.class);
query.select(root);

Subquery<Bucket> subquery = query.subquery(Bucket.class);
Root<Bucket> subRootEntity = subquery.from(Bucket.class);
subquery.select(subRootEntity);

Path<?> attributePath = subRootEntity.get("Name");
Predicate pred = criteriaBuilder.equal(attributePath, criteriaBuilder.literal("Bucket_1"));
subquery.where(pred);
query.where(criteriaBuilder.exists(subquery));

TypedQuery<Bucket> typedQuery = em.createQuery(query);

boolean entityExists = typedQuery.getResultList().size() == 1;
select generatedAlias0 from com.test.Bucket as generatedAlias0 where exists (select generatedAlias1 from com.test.Bucket as generatedAlias1 where generatedAlias1.Name=:param0)
boolean result = (session.createCriteria(Bucket.class)
       .add(Restrictions.eq("Name","Bucket_1"))
       .setProjection(Projections.count("Name"))
       .uniqueResult() > 0);