Hibernate——Hql实例+详解
来源:互联网 发布:mac隐藏的照片 编辑:程序博客网 时间:2024/05/18 01:02
Hibernate配备了一种非常强大的查询语言,这种语言看上去很像SQL。完整的HQL语句形式如下:Select/update/delete…… from …… where …… group by …… having …… order by …… asc/desc。同时需要注意的是在hql中关键字不区分大小写,通常小写,类的名称和属性名称必须区分大小写,按照实体的设计去写大小写。
下面从实例入手去进一步说明HQL的语音的用法。
搭建测试环境:
测试中建立一个Classes实体类里面包含属性:id、班级名称、以及学生。student实体类里面包含:id、姓名、创建时间以及班级。student与classes是多对一的关系。
实体类
public class Student {private int id;private String name;private Date createTime;private Classes classes;public Date getCreateTime() {return createTime;}public Student() {}public Student(int id, String name) {this.id = id;this.name = name;}public void setCreateTime(Date createTime) {this.createTime = createTime;}public Classes getClasses() {return classes;}public void setClasses(Classes classes) {this.classes = classes;}public int getId() {return id;}public void setId(int id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}
public class Classes {private int id;private String name;private Set students;public Set getStudents() {return students;}public void setStudents(Set students) {this.students = students;}public int getId() {return id;}public void setId(int id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}}
映射文件:
<hibernate-mapping><class name="com.syq.hibernate.Classes" table="t_classes"><id name="id"><generator class="native"/></id><property name="name"/><set name="students" inverse="true"><key column="classid"/><one-to-many class="com.syq.hibernate.Student"/></set></class></hibernate-mapping>
<hibernate-mapping><class name="com.syq.hibernate.Student" table="t_student"><id name="id"><generator class="native"/></id><property name="name"/><property name="createTime"></property><many-to-one name="classes" column="classid"></many-to-one></class></hibernate-mapping>
1.简单属性查询
单一属性查询,返会属性结果集列表,元素类型和实体类中相应的类型一致
List students=session.createQuery("select name from Student").list();
多个属性查询,多个属性查询返会对象数组,对象数组的长度取决于属性的个数,对象数组中元素的类型取决于属性在实体类中的类型
List students=session.createQuery("select id,name from Student").list();
多个属性查询,也可以使用hql动态实例化Student对象,返回实体对象。
List students=session.createQuery("select new Student(id,name) from Student").list();
2、实体对象查询
N + 1问题
就是发出了N+1条sql语句。1:首先发出查询对象id列表的语句。N:根据id到缓存中查询,如果缓存中不存在与之匹配的数据,那么会根据id发出相应的sql语句
利用Iterator会出现N+1条SQL语句
Iterator iterator=session.createQuery("from Student").iterate();
如果先使用List将数据查询到session中再使用Iterator进行查询,就不会产生N+1条SQL语句,原因是:list: 默认情况下list每次都会发出sql语句,list会将数据放到缓存中,而不利用缓存;iterate:默认情况下iterate利用缓存,如果缓存中不存在会出现N+1问题
List students=session.createQuery("from Student").list();for (Iterator iterator = students.iterator(); iterator.hasNext();) {Student student = (Student) iterator.next();System.out.println(student.getName());}System.out.println("---------------------------------------------");Iterator iterator=session.createQuery("from Student").iterate();while(iterator.hasNext()){Student student=(Student)iterator.next();System.out.println(student.getName());}
3、条件查询
采用拼字符串的方式传递参数
List students = session.createQuery("select s.id, s.name from Student s where s.name like '%0%'").list();
采用 “?”来传递参数(索引从0开始)
List students=session.createQuery("select s.id, s.name from Student s where s.name like ?").setParameter(0, "%0%").list();
采用 “:参数名” 来传递参数
List students=session.createQuery("select s.id, s.name from Student s where s.name like :myname").setParameter(":myname", "%0%").list();
传递多个参数采用setParamterList方法
List students=session.createQuery("select s.id, s.name from Student s where s.id in (?,?,?,?,?)").setParameter(0, 1).setParameter(1, 2).setParameter(2, 3).setParameter(3, 4).setParameter(4, 5).list();或者
List students=session.createQuery("select s.id, s.name from Student s where s.id in (:ids)").setParameterList("ids", new Object[]{1,2,3,4,5}).list();
hql中使用数据库的函数,如:date_format进行查询
List students=session.createQuery("select s.id, s.name from Student s where s.date_format(s.createTime,'%Y-%m')=? ").setParameter(0, "2009-08").list();
4、hibernate直接使用sql语句查询
List students=session.createSQLQuery("select * from t_student").list();
5、外置命名查询
所谓的外置命名查询,就是将需要查询的sql语句以及条件写到映射文件中。
1.在映射文件中使用<query>标签来定义hql
<query name="queryStudent"><span style="white-space:pre"></span><![CDATA[ select s from Student s where s.id<? ]]></query>
2.在程序中使用session.getNamedQuery()方法得到hql查询串
List students=session.getNamedQuery("queryStudent").setParameter(0, 10).list();</span>
6、过滤器查询
过滤器查询在映射文件利用filter-def去定义一个过滤器,在过滤期中定义过滤器写条件。并在程序中为过滤器赋值。
1.在映射文件中定义过滤器参数,在类的映射中使用过滤器参数
<class name="com.syq.hibernate.Student"table="t_student"> <id name="id"> <generator class="native"/> </id> <property name="name"/> <property name="createTime"></property> <many-to-one name="classes"column="classid"></many-to-one> <filter name="testFilter"condition="id < :myid"></filter> </class> <filter-def name="testFilter"> <filter-param name="myid"type="integer"/> </filter-def>
2.在程序中必须显示的启用过滤器,并且为过滤器参数赋值
//启动过滤器,并给过滤器添加条件session.enableFilter("testFilter").setParameter("myid", 10);List students=session.createQuery("from Student").list();
7、分页查询
setFirstResult(),从0开始,setMaxResults(),每页显示的记录数
List students=session.createQuery("from Student").setFirstResult(1).setMaxResults(2).list();
8、对象导航查询
List students=session.createQuery("from Student s where s.classes.name like " +"'%2%'").list();
9、连接查询
内连接
List students=session.createQuery("select s.name,c.name from Student s join s.classes c").list();
左连接
List students=session.createQuery("select s.name,c.name from Student s left join s.classes c").list();
List students=session.createQuery("select s.name,c.name from Student s right join s.classes c").list();
10、统计查询
count
List list=session.createQuery("select Count(*) from Student").list();或者直接返回统计数字
Long count=(Long)session.createQuery("select Count(*) from Student").uniqueResult();
group分组
String hql="select c.name,count(s) from Classes c join c.students s group by c.name" ;List students=session.createQuery(hql).list();
总之,可以利用hql进行灵活查询:进行条件查询、直接使用原生sql查询、外置名称查询、过滤器查询、分页查询、导航属性查询、连接查询、统计查询。但是所有的查询大多数都返回的是数组对象。只有使用“from student”语句、单一属性查询以及l动态实例化实体类对象的时候才能返回实体集合。
参考:王勇老师的《SSH视频》
- Hibernate——Hql实例+详解
- 精通Hibernate——HQL查询详解
- 精通Hibernate——HQL查询详解
- hibernate中的HQL详解(实例)
- Hibernate——HQL
- Hibernate HQL 初步实例
- hibernate hql 使用实例
- Hibernate Hql查询实例
- Hibernate HQL 语法详解
- hibernate hql 详解
- Hibernate HQL语言详解
- Hibernate HQL详解
- Hibernate:HQL详解
- hibernate HQL 语句详解
- Hibernate Hql详解
- Hibernate的HQL详解
- Hibernate HQL详解
- Hibernate HQL详解
- C语言字符数组与字符串简介
- 各种排序总结
- Xcode自动注释插件:VVDocumenter-Xcode
- PHP与Linux进程间的通信
- Java 面试试题及其解答
- Hibernate——Hql实例+详解
- 关于pkg: /data/local/tmp/com.example.zy.deyijia Failure [INSTALL_FAILED_OLDER_SD问题
- leetcode 151: Reverse Words in a String
- Mac下最好用的离线词典-欧陆词典破解版
- hdu 5109 Alexandra and A*B Problem
- POJ 2299 Ultra-QuickSort(求逆序数)
- Sorting It All Out
- 代写代做程序设计 国外算法编程 VB/C语言/C++/数据结构/Java/PHP/Python
- 关于support design包中behaviour的使用