JPA: s'il vous plaît aider à la compréhension “join fetch”
J'ai l'entité suivante de la structure: Entreprise --> Campagne --> la Promotion, où UNE Entreprise peut avoir de NOMBREUSES Campagnes et UNE Campagne peut avoir de NOMBREUSES Promotions. À la fois un-à-plusieurs relations sont déclarées comme des PARESSEUX. Une place à part dans mon code, j'ai besoin de ardemment récupérer à la fois les collections d'une Entreprise, donc je n':
Query query = entityManager.createQuery("select b from Business b " +
"left join fetch b.campaigns c " +
"left join fetch c.promotions where b.id=:id");
query.setParameter("id", b.getId());
business = (Business) query.getResultList().get(0);
Toutefois, la requête renvoie une liste qui contient 4 objets d'Affaires, tous les 4 objets font référence à la même Entreprise de l'instance. Dans ma base de données, cette entreprise possède 3 campagnes, et tous les 3 campagnes ont 3 promotions en vertu de l'.
J'ai deux questions:
- Au premier abord, j'utilise de la Liste contient de nombreux côtés de la les relations, mais lorsque le programme s'exécute, j'obtiens un "org.mise en veille prolongée.HibernateException: ne peut pas simultanément extraire plusieurs sacs de" l'exception". Alors j'ai googlé cette exception et il semble que je dois utiliser Ensemble, au lieu de la Liste. J'ai donc changé la collection de Jeu et cela a fonctionné. Quelqu'un peut-il me dire pourquoi la Liste ne fonctionne pas dans cette situation?
- Je m'attends à ce que la requête renvoie un résultat unique, parce que c'est d'interroger l'identité, qui est la clé primaire, et donc ne doit retourner qu'un seul résultat. Mais il s'avère qu'il renvoie 4 cas dans une Liste. Est-ce un problème? Ou est-ce un comportement normal?
Toute aide sera grandement appréciée.
OriginalL'auteur Tong Wang | 2009-02-26
Vous devez vous connecter pour publier un commentaire.
Le sql généré ressemblerait à quelque chose comme:
Interne de la veille prolongée une seule instance d'Affaires, cependant, les doublons seront conservés dans le jeu de résultats. Ce comportement est normal. Le comportement que vous avez besoin peut être obtenue soit à l'aide de la clause DISTINCT, ou à l'aide d'un LinkedHashSet pour filtrer les résultats:
qui sera de retour que des résultats uniques, la préservation de l'ordre d'insertion.
Le "org.mise en veille prolongée.HibernateException: impossible d'extraire simultanément plusieurs sacs" se produit chaque fois que vous essayez d'impatience chercher plus d'une collection, d'une manière ordonnée (et éventuellement d'éléments dupliqués). Ce n'trier de faire sens si l'on considère le SQL généré. Hibernate n'a aucun moyen de savoir si un objet dupliqué a été causé par la jointure ou par réel des données en double dans la table enfant. Regardez cette pour une bonne explication.
OriginalL'auteur Il-Bhima
OriginalL'auteur xocasdashdash
Je suppose que si vous utilisez une Liste, hibernate suppose que l'ordre est important, et il va en déduire l'ordre des éléments de la lignes renvoyées, mais si vous jointure avec une autre table hibernate obtiendrez chaque campagne plusieurs fois qui confond la mise en veille prolongée. Encore une fois, je suis juste en supposant que ce
Ce comportement est normal d'Utiliser une RootEntityResultTransformer pour obtenir une racine unique entité: http://www.hibernate.org/hib_docs/v3/api/org/hibernate/transform/RootEntityResultTransformer.html
OriginalL'auteur Jens Schauder
Une autre solution au lieu de l'aide de Jeu est d'utiliser deux requêtes pour obtenir les données :- 1er à la charge de la campagne et de ses promotions de l'entreprise. Ensuite, la charge de l'Entreprise et de ses campagnes à l'aide d'extraire
OriginalL'auteur Manu