55 votes

Quelle est la différence entre les opérateurs IN et MEMBER OF JPQL ?

Quelle est la différence entre le IN y MEMBER OF Opérateurs JPQL ?

65voto

Mikko Maunu Points 20360

Les tests IN sont la valeur de l'expression de chemin à valeur unique (attribut persistant de votre entité) dans les valeurs que vous avez fournies à la requête (ou récupérées via une sous-requête).

Les tests MEMBER OF sont des valeurs que vous avez fournies pour interroger (ou définies avec une expression) les membres des valeurs d'une collection de votre entité.

Prenons l'exemple de l'entité suivante :

@Entity
public class EntityA {
    private @Id Integer id;
    private Integer someValue;
    @ElementCollection
    List<Integer> listOfValues;

    public EntityA() { }

    public EntityA(Integer id, Integer someValue, List<Integer> listOfValues) {
        this.id = id;
        this.someValue = someValue;
        this.listOfValues = listOfValues;
    }
}

Et les données de test suivantes :

EntityA a1 = new EntityA(1, 1, Arrays.asList(4, 5, 6));
EntityA a2 = new EntityA(2, 2, Arrays.asList(7, 8, 9));

Avec la requête suivante, nous obtenons a1 comme résultat, car sa someValue est l'une des (0,1,3). En utilisant des littéraux dans la requête ( SELECT a FROM EntityA a WHERE a.someValue IN (0, 1, 3) ) produit le même résultat.

TypedQuery<EntityA> queryIn = em.createQuery(
    "SELECT a FROM EntityA a WHERE a.someValue IN :values", EntityA.class);
queryIn.setParameter("values", Arrays.asList(0, 1, 3));
List<EntityA> resultIn = queryIn.getResultList();

Avec la requête suivante, nous obtenons a2 comme résultat, car 7 est l'une des valeurs de listOfValues :

TypedQuery<EntityA> queryMemberOf = em.createQuery(
    "SELECT a FROM EntityA a WHERE :value MEMBER OF a.listOfValues", EntityA.class);
queryMemberOf.setParameter("value", 7);
List<EntityA> resultMemberOf = queryMemberOf.getResultList();

Cette fonctionnalité (y compris la collection comme paramètre) est définie dans la spécification JPA 2.0 et n'est pas spécifique à Hibernate (le code ci-dessus fonctionne par exemple avec EclipseLink).

26voto

Michael Borgwardt Points 181658

IN teste si une valeur fait partie d'une liste fixe explicite de littéraux ou de paramètres de requête.

MEMBER OF teste si une valeur est présente dans une collection JPA, c'est-à-dire une collection qui fait réellement partie du modèle objet.

0 votes

Je ne sais pas si c'est un truc spécifique à Hibernate, mais IN fonctionne avec les collections ici... mais membre de semble plus approprié de toute façon.

0 votes

En utilisant JPA avec Hibernate comme fournisseur, l'utilisation de IN n'a pas fonctionné. Il fallait utiliser MEMBER OF.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X