通过集合集选择实体

时间:2014-03-10 04:16:32

标签: java-ee jpa jpql

我正在尝试执行以下操作的JPQL查询或JPA操作。我有一个元素,由字符串的元素集合组成:

@Entity(name="REQUEST")
public class Request {

    @ElementCollection
    private Set<String> keywords;
    ...    
}

我希望能够选择关键字与给定字符串集完全匹配的实体。我已经研究过使用IN但如果只存在一个关键字则会匹配。如果所有关键字都存在,我该如何匹配?

1 个答案:

答案 0 :(得分:2)

我能想到的最简单的方法是进行两次计数查询:

  1. 集合中关键字数量的计数
  2. 不在集合中的关键字数量
  3. #1的结果应该等于集合中的关键字数量。 #2的结果应该等于0.例如:

    List<Request> requests = 
      em.createQuery("select r from Request r " +
                     "where (select count(k1) from Request r1 " +
                     "       join r1.keywords k1 " +
                     "       where r1 = r and k1 in :keywords) = :numKeywords " +
                     "and (select count(k2) from Request r2 " +
                     "     join r2.keywords k2 " +
                     "     where r2 = r and k2 not in :keywords) = 0", Request.class)
         .setParameter("keywords", keywords)
         .setParameter("numKeywords", keywords.size())
         .getResultList();
    

    如果您关心的是该集合是否是请求关键字的子集,则不需要第二次计数。这可以通过以下方式在一个查询中完成:

    List<Request> requests = 
          em.createQuery("select r from Request r " +
                         "join r.keywords k " +
                         "where k in :keywords " +
                         "group by r " +
                         "having count(r) = :numKeywords", Request.class)
            .setParameter("keywords", keywords)
            .setParameter("numKeywords", keywords.size())
            .getResultList();