【hibernate】——hql简单属性+实体对象查询

网友投稿 798 2022-10-13

【hibernate】——hql简单属性+实体对象查询

【hibernate】——hql简单属性+实体对象查询

最近一直在研究hibernate,真是觉得越深入乐趣越多,由衷佩服hibernate的开发者,真正的体验到什么时灵活自如!真的很喜欢!     本文小编主要讲解hibernate中原生sql在查询简单属性和实体对象的怎么使用,以及几种不同的参数查询。

简单属性查询

1】 单个属性

//返回结果集属性列表,元素类型和实体类中的属性类型一致,其中Student对应的是程序中实体List students = session.createQuery("select name from Student").list();for (Iterator iter=students.iterator(); iter.hasNext();){ String name = (String)iter.next(); System.out.println(name);}

2】 多个属性

//查询多个属性,返回对象数组集合//数组元素的类型与查询的属性类型一致//数组的长度与select中查询的属性个数一致List students = session.createQuery("select id, name from Student").list();for (Iterator iter=students.iterator(); iter.hasNext();) { Object[] obj = (Object[])iter.next(); System.out.println(obj[0] + ", " + obj[1]);}

在是使用原生sql的时候可以采用别名,或者采用as命名别名的方法进行处理,同样在hql支持

// 可以使用别名List students = session.createQuery("select s.id, s.name from Student s").list();// 可以采用as命名别名List students = session.createQuery("select s.id, s.name from Student as s").list();

3】 参数查询

1) 单个属性查询

a)拼串

// 可以拼串List students = session.createQuery("select id,name from Student where name like '%0%'").list();

b)占位符

List students = session.createQuery("select id,name from Student where name like ?") .setParameter(0, "%0%").list();

c)冒号 参数名

List students = session.createQuery("select id,name from Student where name like :myname") .setParameter("myname", "%0%").list();

2) 多个属性查询

a)占位符

List students = session.createQuery( "select id,name from Student where id in(?,?,?,?,?)") .setParameter(0, 1) .setParameter(1, 2) .setParameter(2, 3) .setParameter(3, 4) .setParameter(4, 5) .list();

b)参数名

List students = session.createQuery("select id,name from Student where id in(:ids)") .setParameterList("ids", new Object[]{1,2,3,4,5}) .list();

上述两种方式哪种更好?

小编更推荐第二种,理由当参数的个数的发生变化时,方法二需要改动地方更少,更加灵活,简便。

实体对象查询

1】 List

提示:注意观察执行hql的时候select可以忽略,同时执行此查询仅仅发出了一条sql,对比下面的iterate

2】iterate

Iterator iter = session.createQuery("from Student").iterate(); while (iter.hasNext()) { Student student = (Student) iter.next(); System.out.println(student.getName()); }

提示:使用迭代后执行此hql,在控制台会出现N+1条sql语句,从系统执行的效率来说是低下,不值得使用,但是还是应该分析利弊再决定!

3】 List和iterate使用规范

上述说到iterate出现N+1问题,那我们就拒绝使用迭代么!其实不是这样,下面做二个demo

1、list查询之后再使用list查询

@SuppressWarnings("unchecked") public void testQuery4() { Session session = null; try { session = HibernateUtils.getSession(); session.beginTransaction(); List students = session.createQuery("from Student").list(); for (Iterator iterator = students.iterator(); iterator.hasNext();) { Student student = (Student) iterator.next(); System.out.println(student.getId() + ";" + student.getName()); } System.out.println("-----------------------------"); /** * 再次发出查询语句 * * 默认情况下,每次执行list查询实体对象都会发出查询语句,除非配置了查询缓存 * 虽然一级缓存中存在student数据,但list不用,仍然发出查询语句 * * 其实list就是只向缓存中放入数据,而不利用缓存中的数据 */ students = session.createQuery("from Student").list(); for (Iterator iterator = students.iterator(); iterator.hasNext();) { Student student = (Student) iterator.next(); System.out.println(student.getId() + ";" + student.getName()); } session.getTransaction().commit(); } catch (Exception e) { e.printStackTrace(); session.getTransaction().commit(); } finally { HibernateUtils.closeSession(session); } }

2、先用list查询,再使用iterate查询

@SuppressWarnings("unchecked") public void testQuery3() { Session session = null; try { session = HibernateUtils.getSession(); session.beginTransaction(); List students = session.createQuery("from Student").list(); for (Iterator iterator = students.iterator(); iterator.hasNext();) { Student student = (Student) iterator.next(); System.out.println(student.getId() + ";" + student.getName()); } System.out.println("-----------------------------"); /** * 避免N+1问题 因为执行list操作后会将数据放到session的缓存中,所以采用iterator的时候 * 首先会发出一条查询id列表的语句,在根据id到缓存中加载相应的数据。如果缓存中存在与之匹配的数据, * 则不再发出根据id查询的sql语句,直接使用缓存中的数据 * iterate方法,如果缓存中存在数据,它可以提高性能,否则出现N+1问题 */ Iterator iter = session.createQuery("from Student").iterate(); while (iter.hasNext()) { Student student = (Student) iter.next(); System.out.println(student.getName()); } session.getTransaction().commit(); } catch (Exception e) { e.printStackTrace(); session.getTransaction().commit(); } finally { HibernateUtils.closeSession(session); } }

两者需要根据使用情况考虑,如果内存已经存在数据了,那么使用iterate完美满足。如果内存中没有,还是先使用list。

【总结】

关于hql这一部分因为sql的基础,接触起来还是比较容易。关于hql查询这一部分内容基本上这么多了,返回属性和返回实体基本没有差别,还有关于list和iterate这两个使用情况一定要分区情况,所有都是为了程序有更好的性能!

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:fw4j- mvc框架
下一篇:CXPHP- PHP框架(超纤皮和皮革的区别)
相关文章

 发表评论

暂时没有评论,来抢沙发吧~