Hibernate Criteria中的三种Distinct

案例:

/**
 * 客户拜访计划
 * 
 **/
@Entity
@Table(name = "cus_visit")
public class Visit {
	/**
	 * 同行人
	 */
	private Set<Employee> partners;
	@ManyToMany(targetEntity = Employee.class, cascade = { CascadeType.MERGE },fetch = FetchType.LAZY)
	@Cascade(value = { org.hibernate.annotations.CascadeType.SAVE_UPDATE,org.hibernate.annotations.CascadeType.DELETE })
	@JoinTable(name = "cus_visit_employee", joinColumns = { @JoinColumn(name = "visit_id") }, inverseJoinColumns = { @JoinColumn(name = "employee_id") })
	@Fetch(FetchMode.SELECT)
	public Set<Employee> getPartners() {
		return partners;
	}
	public void setPartners(Set<Employee> partners) {
		this.partners = partners;
	}
}

Criteria创建:

Criteria criteria = getSession().createCriteria(Visit.class)
				.setFirstResult(pageInfo.getStartIndex())
				.setMaxResults(pageInfo.getNumPerPage());

查询条件

private void addQueryCause(Criteria criteria, Visit visit) {
criteria.createAlias("partners", "partner");
if(visit.getPartners()!=null){
			Set<Employee> partnerSet = visit.getPartners();
			for(Employee employee :partnerSet){
				criteria.add(Restrictions.or(Restrictions.like(
						"partner.empNo", employee.getEmpNo(),MatchMode.ANYWHERE),Restrictions.like(
						"partner.name", employee.getName(),MatchMode.ANYWHERE)));
				}
			
		}
//其他查询条件...
}

第一种:对查询完毕之后的结果进行Distinct

addQueryCause(idsOnlyCriteria, visit);
criteria.setResultTransformer(criteria.DISTINCT_ROOT_ENTITY);
return criteria.list();



第二种:只查询一个属性,并对这个属性进行Distinct

addQueryCause(idsOnlyCriteria, visit);
criteria.setProjection(Projections.distinct(Projections.id()));
return criteria.list();



第三种:使用子查询,实现整条记录的Distinct

DetachedCriteria idsOnlyCriteria = DetachedCriteria.forClass(Visit.class);
idsOnlyCriteria.setProjection(Projections.distinct(Projections.id()));
addQueryCause(idsOnlyCriteria, visit);

criteria.add(Subqueries.propertyIn("id", idsOnlyCriteria));

return criteria.list();

第三种实现依赖于第二种功能,把条件都放到对id查询的限制上,之后在查询主记录只需要使主键IN子查询结果就行了。最后生成的SQL语句:

    select
        this_.id as id1_61_0_,
       ....
    from
        cus_visit this_ 
    where
        this_.id in (
            select
                distinct this_.id as y0_ 
            from
                cus_visit this_ 
            left outer join
                cus_visit_employee partners3_ 
                    on this_.id=partners3_.visit_id 
            left outer join
                core_employee partner1_ 
                    on partners3_.employee_id=partner1_.emp_no 
            where
                (
                    this_.planer=? 
                    or partner1_.emp_no=?
                )
        ) 
    order by
        this_.id asc limit ?




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值