迫切左外连接

2.更深层次的级联左外连接时:

String hql = "from User u LEFT OUTER JOIN FETCH u.shoppingCartSet "
+ "LEFT OUTER JOIN FETCH u.shoppingCart.book where u.id = ?";        

会报could not resolve property: shoppingCart of: entities.User [from entities.User u LEFT OUTER JOIN FETCH u.shoppingCartSet sc LEFT OUTER JOIN FETCH u.shoppingCart.book where u.id = ?]

 而这样写就可以解决

String hql = "from User u LEFT OUTER JOIN FETCH u.shoppingCartSet sc "
+ "LEFT OUTER JOIN FETCH sc.book where u.id = ?";

以下是另一种情况

String hql = "from ShoppingCart sc left outer join fetch sc.book left outer join fetch sc.user.name "
+ "where sc.user.id = ?";      会报空指针异常

但把.name去掉就不会了

String hql = "from ShoppingCart sc left outer join fetch sc.book left outer join fetch sc.user "
+ "where sc.user.id = ?";

1.left outer join fetch语句要放在where前面才行


package jiansuo_jiben;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashSet;
import java.util.List;

import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.hibernate.service.ServiceRegistry;
import org.hibernate.service.ServiceRegistryBuilder;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

public class TestFetch {
    private SessionFactory sessionFactory;
    private Session session;
    private Transaction transaction;
    @Before
    public void before(){
        Configuration configuration  = new Configuration().configure();
        ServiceRegistry serviceRegistry = new ServiceRegistryBuilder().applySettings(configuration.getProperties())
                                                                        .buildServiceRegistry();
        sessionFactory = configuration.buildSessionFactory(serviceRegistry);
        session = sessionFactory.openSession();
        transaction = session.beginTransaction();
    }
    @After
    public void after(){
        transaction.commit();
        session.close();
        sessionFactory.close();
    }
    
    /**Left join Fetch是迫切左外连接
     * 1,查询到的List中是Department实体对象
     * 2,且每一个实体对象中的Employee对象也已被初始化
     * 
     * */
    @Test
    public void testFetch() {
        String hql = "FROM Department d Left join Fetch d.set";
        Query q = session.createQuery(hql);
        List<Department> ds = q.list();
        for(Department d:ds){
            System.out.println(d +":"+ d.getSet().size());
        }
    }
    /**
     * 对于迫切左外连接
     * 两种方法去重
     * 且在加载department时就将其set属性初始化(这是与左外连接的区别)(相当于强制去掉懒加载)
     * */
    @Test
    public void testFetch2() {
//        String hql = "Select distinct d FROM Department d Left join Fetch d.set";
        String hql = "FROM Department d Left join Fetch d.set";
        Query q = session.createQuery(hql);
        List<Department> ds = q.list();
        ds = new ArrayList<>(new LinkedHashSet<>(ds));
        for(Department d:ds){
            System.out.println(d +":"+ d.getSet().size());
        }
    }
    /**左外连接
     * 1,返回的List中存放的是Object[],[0]中是Department[1]中是Employee
     * 2,用到Department中的set时还需select,根据配置文件来决定 Employee 集合的检索策略. 
     * */
    @Test
    public void testFetch3() {
//        String hql = "Select distinct d FROM Department d Left join Fetch d.set";
        String hql = "FROM Department d Left join d.set";
        Query q = session.createQuery(hql);
        List<Object[]> ds = q.list();
//        ds = new ArrayList<>(new LinkedHashSet<>(ds));
        for(Object[] d:ds){
            System.out.println(Arrays.asList(d));
            System.out.println(((Department)d[0]).getSet());
        }
    }
    /**
     * 只用这种方式去重,
     * 因为上一个方法返回的List中是数组所以不能通过LinkedHashSet去重
     * */
    @Test
    public void testFetch4() {
        String hql = "Select distinct d FROM Department d Left join d.set";
        Query q = session.createQuery(hql);
        List<Department> ds = q.list();
//        ds = new ArrayList<>(new LinkedHashSet<>(ds));
        for(Department d:ds){
            System.out.println(Arrays.asList(d));
            System.out.println(d.getSet());
        }
    }
}
原文地址:https://www.cnblogs.com/feifeiyun/p/6476411.html