时间:2017-1-22 16:09

——检索方式

Hibernate中提供了以下几种检索对象的方式:
    *   导航对象图检索方式
        根据已经加载额对象导航到其他对象。
        >   Customer customer = (Customer)session.get(Customer.class, 1)
            customer.getOrders(); // 得到客户的订单

    *   OID检索方式
        按照对象的OID来检索对象。
        >   get() / load()

    *   HQL检索方式
        使用面向对象的HQL查询语言。
        >   Query query = session.createQuery(String HQL)

    *   QBC检索方式
        使用QBC API来检索对象,这种API封装了基于字符串形式的查询语句,提供了更加面向对象的查询接口。
        >   Criteria criteria = session.createCriteria(Customer.class)

    *   本地SQL检索方式
        使用本地数据库的SQL查询语句。
        >   SQLQuery quer = session.createSQLQuery(String sql)

——HQL

1、HQL(Hibernate Query Language)是面向对象的查询语言,它和SQL查询语言有些相似,在Hibernate提供的各种检索方式中,HQL是使用最广泛的一种检索方式,它有如下功能:
    *   在查询语句中设定各种查询条件
    *   支持投影查询,即仅检索出对象的部分属性
    *   支持分页查询
    *   支持连接(多表)查询
    *   支持分组查询,允许使用HAVING和GROUP BY关键字
    *   提供内置函数,如SUM(),MIN(),MAX()
    *   能够调用用户自定义的SQL函数或标准的SQL函数
    *   支持子查询
    *   支持动态绑定参数

2、HQL检索方式包括以下步骤
    *   通过Session的createQuery()方法创建一个Query对象,它包括一个HQL查询语句,HQL查询语句中可以包含命名参数。
    *   动态绑定参数
    *   调用Query的list()方法执行查询语句,该方法返回java.util.List类型的查询结果,在List集合中存放了复合查询条件的持久化对象。

3、Query接口支持方法调用链编程风格,它的setXxx()方法返回自身实例,而不是void类型

4、HQL和SQL的区别
    1)HQL查询语句是面向对象的,Hibernate负责解析HQL查询语句,然后根据对象 - 关系映射文件中的映射信息,把HQL查询语句翻译成相应的SQL语句,HQL查询语句中的主体是域模型中的类及类的属性。
    2)SQL查询语句是与关系型数据库绑定在一起的,SQL查询语句中的主体是数据库表及表的字段。

示例代码:
    1)使用HQL查询所有数据
        // 使用HQL查询全部客户信息

        // Query query = session.createQuery("from Customer");
        // List<Customer> list = query.list();
        // print(list);

2)使用别名进行查询
        // 使用别名查询

        // List<Customer> list = session.createQuery("from Customer as c").list();
        // print(list);
 
        // 使用别名查询:条件查询,as关键字可以省略
        // 不支持select * from 表的语法,但是可以使用:select 别名 from 表 as 别名
        Query query = session.createQuery("from Customer as c where c.cname = ?");
        // query.setString(0, "张三");
        // 除了setString(),也可以setParameter()
        query.setParameter(0, "张三");
        List<Customer> list = query.list();
        print(list);

    3)多态查询
        会将配置文件中实现了指定类的全部子类都进行查询。
        Query query = session.createQuery("from java.lang.Object");
        print(query.list());

    4)对查询结果进行排序
        List<Customer> list = session.createQuery("from Customer as c order by c.id desc").list();
        print(list); 

    5)分页查询
        // 使用HQL进行分页查询
        Query query = session.createQuery("from Order");
        query.setFirstResult(0);
        query.setMaxResults(11);
        List<Order> list = query.list();
        print(list);

    6)查询单个记录
        // 使用HQL查询单个记录
        Query query = session.createQuery("from Customer where cname = ?");
        query.setString(0, "李四");
        // 当结果超过1条时,uniqueResult()方法会报错
        Customer customer = (Customer) query.uniqueResult();
        System.out.println(customer);

    7)投影查询
        /*
         * 只查询客户的名称
         * 如果只查询一个属性,返回的是String
         * 如果查询多个属性,返回的是一个Object数组
         */
        // Query query = session.createQuery("select c.cid, c.cname from Customer as c");
        // 查询一个属性时,返回字符串
        // List<String> = query.list();
        // 查询多个属性时返回数组
        // List<Object[]> list = query.list();
        /*
         * 将查询记录封装到对象中
         * 为实体类提供一个对应参数的构造方法
         * public Customer(Integer cid, String cname){ ... } 
         */
        Query query = session.createQuery("select new Customer(cid, cname) from Customer");
        List<Customer> list = query.list();
        print(list);

    8)绑定参数,进行条件查询
        // 使用?方式绑定参数
        Query query = session.createQuery("from Customer where cname = ?");
        query.setParameter(0, "李四");
        List<Customer> list = query.list();
        print(list);

        // 多个参数

        Query query = session.createQuery("from Customer where cname = ? and cid = ?");
        query.setParameter(0, "李四");
        query.setParameter(1, 2);
        List<Customer> list = query.list();

print(list);

        // 使用名称方式绑定参数
        Query query = session.createQuery("from Customer where cname = :name and cid = :id");
        query.setParameter("name", "李四");
        query.setParameter("id", 2);
        List<Customer> list = query.list();

print(list);

        // 绑定实体参数
        Customer customer = new Customer();
        customer.setCid(1);
        Query query = session.createQuery("from Order as o where o.customer = ?");
        query.setEntity(0, customer);
        List<Order> list = query.list();

print(list);

    9)模糊查询

        // 使用HQL进行模糊查询
        Query query = session.createQuery("from Customer where cname like ?");
        query.setParameter(0, "李%");
        List<Customer> list = query.list();

print(list);

    10)聚合函数

        // 使用聚合函数查询
        Query query = session.createQuery("select count(*) from Order");
        List<Order> list = query.list();

print(list);

——QBC

QBC运算符:

    

示例代码:
    1)使用QBC查询所有数据
        // 使用QBC的方式查询所有客户信息

        // Criteria criteria = session.createCriteria(Customer.class);
        // print(criteria.list());

2)对查询结果进行排序

        Criteria criteria = session.createCriteria(Customer.class).addOrder(org.hibernate.criterion.Order.desc("id"));
        print(criteria.list());

    3)分页查询

        // 使用QBC进行分页查询
        Criteria criteria = session.createCriteria(Order.class);
        criteria.setFirstResult(0);
        criteria.setMaxResults(11);
        List<Order> list = criteria.list();

print(list);

    4)查询单个记录

        // 使用QBC查询单个记录
        Criteria criteria = session.createCriteria(Customer.class);
        // 设置条件
        criteria.add(Restrictions.eq("cname", "李四"));
        // 只查询第一条记录
        criteria.setMaxResults(1);
        Customer customer = (Customer) criteria.uniqueResult();

System.out.println(customer);

    5)条件查询
        // 绑定一个参数

        Criteria criteria = session.createCriteria(Customer.class);
        criteria.add(Restrictions.eq("cname", "李四"));
        // 绑定多个参数
        criteria.add(Restrictions.eq("cid", "2")); 
        List<Customer> list = criteria.list();
        print(list);

    6)模糊查询
        // 使用QBC进行模糊查询

        Criteria criteria = session.createCriteria(Customer.class);
        criteria.add(Restrictions.like("cname", "李%"));
        List<Customer> list = criteria.list();
        print(list);

——SQL

示例代码:
    1)使用SQL查询所有数据

        // 使用SQL语句查询全部客户信息
        SQLQuery query = session.createSQLQuery("select * from Customer"); 
        List<Object[]> list = query.list();
        printArr(list);
 
    2)使用SQL查询所有数据,并将数据封装到实体对象中
        // 使用SQL查询全部客户信息,并将结果记录封装到实体对象中
        SQLQuery query = session.createSQLQuery("select * from Customer");
        List<Customer> list = query.addEntity(Customer.class).list();
        print(list);

——多表查询

1、普通多表查询
    1)交叉连接
        select * from A,B;
        得到的是笛卡尔积。

    2)内连接
        查询的是两个表的交集
            select * from A inner join B on A.字段 = B.字段;

        隐式内连接:
            select * from A, B where A.字段 = B.字段

    3)外连接
        左外连接
            select * from A left outer join B on A.字段 = B.字段
        右外连接
            select * from A right outer join B on A.字段 = B.字段

2、在HQL中的多表查询
    1)交叉连接
    2)内连接
    3)隐式内连接
    4)迫切内连接
    5)左外连接
    6)迫切左外连接
    7)右外连接

3、示例代码
    1)内连接
        /*

         * HQL内连接查询
         * 查询的是两个表的交集部分
         */
        Query query = session.createQuery("from Customer as c inner join c.orders");
        List list = query.list();
        printArr(list);

2)迫切内连接
        // 迫切内连接,使用一个关键字fetch

        // 如果使用from Customer as c inner join fetch c.orders,则会出现重复的Customer
        // 可以使用distinct关键字去除重复的Customer:select distinct c 
        Query query = session.createQuery("select distinct c from Customer as c  inner join fetch c.orders");
        List list = query.list();
        print(list);

4、左外连接与迫切左外连接的用法与内连接、迫切内连接相同

5、HQL的内连接与迫切内连接的区别:
    内连接查询:
        将数据封装到List<Object[]>中。
    迫切内连接:
        将数据封装到一个List<Customer>中,但是迫切内连接会得到重复的记录,需要使用distinct去重。

——离线条件查询

现在有这么一个表单,可以根据不同的查询条件进行不同的查询操作,但是DAO层无法获取Web层的对象,可以使用离线对象进行操作。

传统方式:
    UserService user = new UserService();
    user.findByCondition(username, sex, edu, tel);
    这样做的局限性在于无法修改上传的内容,不方便扩展。

离线方式:
    获得一个离线的Criteria,在Web层将Criteria对象的条件设置好。
        criteria.add(Restrictions.eq("name", "张三"));
        criteria.add(Restrictions.eq("sex", "男"));

    然后在Web层调用service方法传入Criteria对象,在DAO层获取可执行的离线Criteria对象。

示例代码:

    /*
     * 离线条件查询
     */
    public void fun15(){
        Session session = HibernateUtils.openSession();
        Transaction tx = session.beginTransaction();
 
        // 在Web层创建离线对象
        DetachedCriteria criteria = DetachedCriteria.forClass(Customer.class);
        // 设置参数
        criteria.add(Restrictions.eq("cname", "李四"));
        criteria.add(Restrictions.eq("cid", 2));

 
 
        // 在DAO层获得可执行的Criteria对象
        Criteria criteria2 = criteria.getExecutableCriteria(session);
        List<Customer> list = criteria2.list();
 
        print(list);
 
        tx.commit();
        session.close();
    }

——总结

1、对象导航方式
    *   可以通过一个对象获得到关联对象。

2、根据OID进行检索
    *   get()
    *   load();

3、HQL
    *   session.createQuery(String hql);
    *   简单查询:from Customer
    *   排序:from Customer c order by c.cid desc;
    *   条件查询:位置绑定参数(?),名称绑定参数(:name)
    *   分页查询:query.setFirstResult(int from); query.setMaxResult(int max)
    *   聚合函数:select count(*) from Customer group by cid;
    *   多态查询:from java.lang.Object
    *   投影查询:select cid, cname from Customer
    *   构造方法将查询结果封装成对象:select new Customer(cid, cname) from Customer
    *   多表查询
        >   交叉连接
        >   内连接
        >   迫切内连接
        >   左外连接
        >   迫切左外连接
    *   命名查询

4、QBC
    *   session.createCriteria(Class class);
    *   简单查询
    *   排序查询
    *   条件查询:criteria.add(Restrictions(name, value));
    *   分页查询
    *   离线条件查询

5、SQL
    *   session.createSQLQuery(String sql);

    

Hibernate之检索方式的更多相关文章

  1. Hibernate的检索方式

    Hibernate的检索方式 检索方式(查询的方式) 导航对象图检索方式: 根据已经加载的对象导航到其他对象 Customer customer = (Customer)session.get(Cus ...

  2. 攻城狮在路上(壹) Hibernate(十四)--- Hibernate的检索方式(下)

    本节介绍HQL和QBC的高级用法:各种连接查询.投影查询.报表查询.动态查询.集合过滤和子查询等.另外将归纳优化查询程序代码,从而提高查询性能的各种技巧.一.连接查询: HQL与QBC支持的各种连接类 ...

  3. 攻城狮在路上(壹) Hibernate(十三)--- Hibernate的检索方式(上)

    Hibernate提供了以下几种检索对象的方式: A.导航对象图检索方式. B.OID检索方式.Session.get() load(); C.HQL检索方式.Query. D.QBC检索方式.Que ...

  4. Hibernate的检索方式--查询数据的方式

    Hibernate 提供了以下几种检索对象的方式1导航对象图检索方式: 根据已经加载的对象导航到其他对象(根据已经加载的对象,导航到其他对象-例如一对多的查询)2OID 检索方式: 按照对象的 OID ...

  5. 【Hibernate】检索方式

    一.概述 二.HQL 2.1 简介 2.2 查询所有记录 2.3 查询使用别名 2.4 排序 2.5 分页查询 2.6 单个对象查询 2.7 参数绑定 2.8 投影操作 2.9 模糊查询 2.10 S ...

  6. Hibernate入门6.Hibernate检索方式

    Hibernate入门6.Hibernate检索方式 20131128 代码下载 链接: http://pan.baidu.com/s/1Ccuup 密码: vqlv Hibernate的整体框架已经 ...

  7. [原创]java WEB学习笔记89:Hibernate学习之路-- -Hibernate检索方式(5种),HQL介绍,实现功能,实现步骤,

    本博客的目的:①总结自己的学习过程,相当于学习笔记 ②将自己的经验分享给大家,相互学习,互相交流,不可商用 内容难免出现问题,欢迎指正,交流,探讨,可以留言,也可以通过以下方式联系. 本人互联网技术爱 ...

  8. Hibernate检索方式 分类: SSH框架 2015-07-10 22:10 4人阅读 评论(0) 收藏

    我们在项目应用中对数据进行最多的操作就是查询,数据的查询在所有ORM框架中也占有极其重要的地位.那么,如何利用Hibernate查询数据呢?Hibernate为我们提供了多种数据查询的方式,又称为Hi ...

  9. Hibernate检索方式(转载)

    我们在项目应用中对数据进行最多的操作就是查询,数据的查询在所有ORM框架中也占有极其重要的地位. 那么,如何利用Hibernate查询数据呢?Hibernate为我们提供了多种数据查询的方式,又称为H ...

随机推荐

  1. div标签width:auto无效

    1,因为div标签默认是display:block,独占一行,宽度为父元素的100%,但是高度是auto,跟随内部内容而定.所以要想 设值父元素随子元素的宽高,那么就要设置div标签为display: ...

  2. 队列Queue:任务间的消息读写,安排起来~

    摘要:本文通过分析鸿蒙轻内核队列模块的源码,掌握队列使用上的差异. 本文分享自华为云社区<鸿蒙轻内核M核源码分析系列十三 消息队列Queue>,作者:zhushy . 队列(Queue)是 ...

  3. 光学动作捕捉系统中的反光标识点(Marker点)

    动作捕捉系统本质上是一种定位系统,通常需要在目标物布置定位设备进行追踪.以红外光学为原理的动作捕捉系统,主要由由光学镜头.动作捕捉软件.反光标识点.POE交换机.和若干配件组成,其中反光标识点(Mar ...

  4. 一台电脑安装两个不同版本的MySQL

    背景: 本人电脑上已有mysql-8.0.12-winx64,并且可以使用.但由于工作需要,得使用mysql-5.5.59-winx64,已有mysql-5.5.59-winx64的解压好的安装包 参 ...

  5. Java 给Word添加印章

    一.概述 本文以Java程序代码展示如何给Word文档添加印章,这里添加的印章为.png格式的图片,添加印章即在Word中的指定位置添加印章图片. 基本思路:加载word文档,获取段落,在段落中插入图 ...

  6. leetcode 987 二叉树的垂序遍历

    题目解析 题目意思很简单,就是给你一个二叉树,然后告诉你每个节点都是有位置信息的,即每个节点可以用(x,y)来表示.然后节点位置信息为(x,y)的节点的左节点位置为(x+1,y-1),右节点位置为(x ...

  7. post传参params与body的区别(@RequestParam和@RequestBody的区别)

    1.axios post请求  Content-Type默认为 application/x-www-form-urlencoded,我们传递参数的时,params里面的参数(简单的对象,通过 &quo ...

  8. 10分钟物联网设备接入阿里云IoT平台

    前言最近尝试了一下阿里云IoT物联网平台,还是蛮强大的.在此记录一下学习过程.本教程不需要任何外围硬件,一台电脑和一根能上网的网线即可.算是一篇Hello World了.先上效果图 第一章 准备工作1 ...

  9. npm命令,nrm命令,n命令, nvm命令

    npm命令 npm/yarn config set registry https://registry.npm.taobao.org 设置淘宝镜像npm/yarn config get registr ...

  10. phpmyadmin error:#2002 - 服务器没有响应 (或者本地 MySQL 服务器的套接字没有正确配置)

    1. 将 "phpMyAdmin/libraries"文件夹下的config.default.php文件中的$cfg['Servers'][$i]['host'] = 'local ...