• Hibernate


    总结

    1.HQL (Hibernate Query Language)

    • 语法类似sql
    • 把sql语句的表名换成了类名,把字段名换成实体类中的属性
    • 具有跨数据库的优点

    2.QBC (Query By Criteria)

    这种方式比较面向对象方式,重点是有三个描述条件的对象:Restrictions,Order,Projections。使用QBC查询,一般需要以下三个步骤 (只有"DetachedCriteria离线查询"不同, 详见示例) :
    • 使用Session实例的createCriteria(XXX.class)方法创建Criteria对象;
    • 使用工具类Restrictions的方法为Criteria对象设置查询条件,Order工具类的方法设置排序方式,Projections工具类的方法进行统计和分组;
    • 使用Criteria对象的list()方法进行查询并返回结果。

    3.SQL (Structured Query Language)

    • 违背了hibernate的跨平台优点,不易维护,不面向对象。不推荐使用。

    HQL示例

    参考:https://www.cnblogs.com/jasonjson/p/12430917.html

    查询所有,条件查询,排序查询,分页查询,统计查询,投影查询

    import com.utils.HibernateUtils;
    import org.hibernate.Query;
    import org.hibernate.Transaction;
    import org.hibernate.classic.Session;
    import org.junit.Test;
    
    import java.util.List;
    
    public class CustomerTestDemo06 {
        /**
         * HQL查询
         * 把sql语句的表明换成了类名。把字段名换成实体类中的属性
         */
        //查询所有
        @Test
        public void  test01(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            Query query=s.createQuery("from Customer");
            List list = query.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //按条件查询--1.占位符
        @Test
        public void  test02(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            Query query=s.createQuery("from Customer where lovel = ? or name like ?");
            query.setString(0,"做县官");  //占位符从0开始的
            query.setString(1,"%刘%");
            List list = query.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //按条件查询--2.给占位符取名字
        @Test
        public void  test03(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //给参数区名 :名  规范是(:属性)
            Query query=s.createQuery("from Customer where lovel = :a or name like :name");
    //        query.setString("a","做县官");  //占位符从0开始的
    //        query.setString("name","%刘%");
            //setParameter()方法,此参数类型更灵活
            query.setParameter("a","做县官");
            query.setParameter("name","%刘%");
            List list = query.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //排序查询
        @Test
        public void  test04(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //order by 列明 desc
            Query query=s.createQuery("from Customer  order by id desc ");
            List list = query.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        /**
         * 分页查询,hibernate提供高了两个方法:
         * setFirstResult(),设置开始查询记录索引
         * setMaxResults(),设置每页查询条数
         *
         */
        @Test
        public void  test05(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //order by 列明 desc
            Query query=s.createQuery("from Customer  order by id desc ");
            query.setFirstResult(3);
            query.setMaxResults(3);
            List list = query.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        /**
         * 统计查询,使用聚合函数:
         *count sum avg max min
         */
        @Test
        public void  test06(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //order by 列明 desc
            Query query=s.createQuery("select count(*) from Customer");
            /*List list = query.list();
            for (Object o : list) {
                System.out.println(o);
            }*/
            Object o = query.uniqueResult(); //当返回结果唯一的时候使用此方法
            System.out.println(o);
            tx.commit();
        }
    
        /**
         * 投影查询:
         * 查询结果只需要部分字段,不需要全部不,且希望返回的结果是封装类,而不是Object
         * 用法:用在HQL语句中new 一个对象,并给对象一个具体的带参的构造函数
         */
        @Test
        public void  test07(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //order by 列明 desc
            Query query=s.createQuery("select new com.bean.Customer(id,name) from Customer");
            List list = query.list();
            for (Object o : list) {
                System.out.println(o);
            }
            tx.commit();
        }
    }
    

    HBC示例

    参考:https://www.cnblogs.com/jasonjson/p/12430917.html

    • Criteria 基本查询,条件查询,排序查询,分页查询,统计(投影)查询,
    • DetachedCriteria 离线查询
    package com.bean;
    
    import com.utils.HibernateUtils;
    import org.hibernate.Criteria;
    import org.hibernate.Query;
    import org.hibernate.Transaction;
    import org.hibernate.classic.Session;
    import org.hibernate.criterion.*;
    import org.junit.Test;
    
    import java.util.List;
    
    public class CustomerTestDemo07 {
        /**
         * QBC查询
         * 更加面向对象的查询方式,它把生成语句的过程全都融入到方法之中
         * 效率比HQL查询慢
         */
        //基本查询
        @Test
        public void  test01(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //获取Criteria对象
            Criteria criteria = s.createCriteria(Customer.class);
            List list = criteria.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //条件查询
        @Test
        public void  test02(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //获取Criteria对象
            Criteria criteria = s.createCriteria(Customer.class);
            //添加查询条件
            criteria.add(Restrictions.eq("lovel", "做县官"));
            criteria.add(Restrictions.like("name", "%张%"));
            List list = criteria.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //分页查询
        @Test
        public void  test03(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //获取Criteria对象
            Criteria criteria = s.createCriteria(Customer.class);
            //设置分页
            criteria.setFirstResult(0);//起始下标
            criteria.setMaxResults(2);  //每页显示条数
            List list = criteria.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //排序查询
        @Test
        public void  test04(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //获取Criteria对象
            Criteria criteria = s.createCriteria(Customer.class);
            //添加查询条件
            criteria.addOrder(Order.desc("name"));
            List list = criteria.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
        //统计查询
        //使用sql自带的聚合函数
        @Test
        public void  test05(){
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //获取Criteria对象
            Criteria criteria = s.createCriteria(Customer.class);
            //添加查询条件
            criteria.setProjection(Projections.count("id"));
            Object o = criteria.uniqueResult();
            System.out.println(o);
            tx.commit();
        }
    
        //离线查询
        //先用离线对象将查询条件封装,再交给session
        @Test
        public void test06(){
            //1.获取DetachedCriteria离线对象
            DetachedCriteria dc=DetachedCriteria.forClass(Customer.class);
            //2.封装查询条件
            dc.add(Restrictions.eq("lovel", "做县官"));
            dc.add(Restrictions.like("name", "%张%"));
            //3.获取session对象,开始事务
            Session s=HibernateUtils.getCurrnetSession();
            Transaction tx = s.beginTransaction();
            //4.将离线对象转成Criteria对象
            //Session s1=HibernateUtils.getCurrnetSession();
            Criteria criteria = dc.getExecutableCriteria(s);
            //5.执行查询
            List list = criteria.list();
            for (Object o : list) {
                System.out.println((Customer)o);
            }
            tx.commit();
        }
    
    
    
    
    
    }
    

    SQL示例

    static List sql() {
       Session s = HibernateUtil.getSession();
        Query q = s.createSQLQuery("select * from user").addEntity(User.class);
        List<User> rs = q.list();
        s.close();
        return rs;
    }
    

    为何有了Criteria,还需要DetachedCriteria?

    参考:https://www.cnblogs.com/jinsheng1027/p/11327159.html

    我的理解:

    为了“解耦”,解除Criteria和session的依赖关系。
    
    Criteria是在线的,所以它是由Hibernate Session进行创建的;
    DetachedCriteria是离线的,创建时无需Session,它通过2个静态方法forClass(Class) 或 forEntityName(Name) 进行DetachedCriteria 的实例创建。
     
    所以DetachedCriteria也称为离线条件查询,即建立一个DetachedCriteria对象,将查询的条件等指定好,然后在session.beginTransaction()后将这个对象传入通常这个对象可以在表示层建立,然后传入业务层进行查询。这样,就解耦了DetachedCriteria与session的依赖。

    HQL与QBC的区别

    参考:https://blog.csdn.net/liuchangjie0112/article/details/51567321

    两者优缺点

    比较方面

    HQL检索方式

    QBC检索方式

    可读性

    和SQL查询语言比较接近,比较容易读懂

    QBC把查询语句肢解为一组Criterion实例。可读性差。

    功能

    功能最强大,支持各种各样的查询。

    没有HQL的功能强大,例如不支持报表查询和子查询,而且对连接查询也做了很多限制。

    查询语句形式

    应用程序必须提供基于字符串形式的HQL查询语句。

    QBC检索方式封装了基于字符串形式的查询语句,提供了更加面向对象的接口。

    何时被解析

    HQL查询语句只有在运行时才会被解析

    OBC在编译时就能被编译,因此更加容易排错

    可扩展性

    不具有扩展性

    允许用户扩展Criterion接口

    对动态查询语句的支持

    尽管支持生成动态查询语句,但是编程很麻烦

    适合于生成动态查询语句

    连接查询的支持

    指定的连接查询类型

    HQL语法

    QBC语法

    适用范围

    内连接

    inner join或者join

    Criteria.createAlias()

    适用于有关联关系的持久化类,并且在映射文件中对这种关联关系作了映射。

    迫切内连接

    inner join fetch或者join fetch

    不支持

    隐式内连接

    不支持

    左外连接

    left outer join或者left join

    不支持

    迫切左外连接

    left outer join fetch或者left join fetch

    FetchMode.EAGER

    右外连接

    right outer join或者right join

    不支持

    交叉连接

    ClassA,ClassB

    不支持

    适用于

  • 相关阅读:
    【转】jquery-取消冒泡
    【转】android如何浏览并选择图片 音频 视频
    ListView防止滑动变色的小技巧
    【转】 Android经验: proguard 阻碍 webview 正常工作
    【转】获取android设备 id
    【转】android 选取图片
    eclipse 配置git ssh登录
    android 开启或者隐藏软键盘
    【转】如何设置Android软键盘的默认不弹出?
    【转】中国人唯一不认可的成功——就是家庭的和睦,人生的平淡
  • 原文地址:https://www.cnblogs.com/frankcui/p/13946674.html
Copyright © 2020-2023  润新知