zoukankan      html  css  js  c++  java
  • Hibernate入门5持久化对象关系和批量处理技术

    Hibernate入门5持久化对象关系和批量处理技术 20131128

    代码下载 链接: http://pan.baidu.com/s/1Ccuup 密码: vqlv

    前言:

             前面学习了Hibernate数据库表之间存在依赖关系的情况,在Hibernate中配置,这样在实际开发中会大大减少SQL的编写量。现在进一步深入Hibernate的级联关系。

    1.级联关系

    在Hibernate中持久化对象之间通过相互关联互相引用,对象进行保存、更新和删除的时候,关联的对象也会执行相对应的操作,这些使用Hibernate中的cascade实现。比如当试图删除一个顾客的时候,级联可以让hibernate决定是否删除该顾客的订单。cascade是<set>中的一个属性,可以选取的值如下:

    none: default,表示关联对象之间是无级联操作的

    save-update:表示主动方对象在调用save() update() saveOrUpdate()方法的时候对被关联对象执行保存或者是更新操作。

    delete: 表示主动方对象在调用delete的时候被关联对象执行删除操作

    delete-orphan

    all:表示save-update和delete的结合

             也就是说,创建一个Customer,给customer中的order添加订单,那么保存customer的时候,也会保存order的信息。

             同时还存在一种反向控制,使用<set>元素中的inverse属性控制,inverse=”true”表示关联关系有N方维护,这样当新建一个订单的时候,使用order.setCustomer(),保存customer的时候,同样也会保存订单信息。

    2.一对一的关联关系

             基于外键的单项1-1

             <many-to-one name="idCard" class="IdCard" cascade="all" column="idcard_id" unique="true"/>

        也就是N方式唯一的,这样就是一对一的关系了

        基于主键的双向的1-1

        上面的方式,可以考虑使用<one-to-one>的方式

        <one-to-many>

    单项的N-N关系

        Order.java中添加字段Set<Product> products以及相应的getter & setter

    <set name=”products” table=”orderitem”>

            <key column=”order_id”/>

            <many-to-many class=”Product” columns=”product_id”/>

        </set>

        这样会生成一张表orderitem,其中只有两个字段 order_id and product_id

    好乱的关系啊,不学了,稍后在学吧

    3.Hibernate批量处理技术

        当需要同时网数据库中添加多条数据的时候,需要使用到批量处理技术。

    3.1批量插入

        public static void addCustomers(){

            Session session = HibernateUtil.getSession();

            Transaction trans = session.beginTransaction();

           

            for(int i = 0; i< 10; i++){

                Customer customer = new Customer("yang","123456","890","广州","15800027127","hbhz.sysu.tengfei@qq.com");

                session.save(customer);

            }

            trans.commit();

            HibernateUtil.closeSession();

           

        }

    在没有学习批量处理之前我们,会想到使用这种方法,因为hibernate本身是有一个一级缓存的,也就是Session缓存,当session中的对象过多的时候,程序会出现运行失败的情况,并且抛出内存溢出的异常OutOfMemoryException

        为了解决这个问题,可以定时的将Session缓存中的数据刷新导数据库中而不是一直缓存在Session中,比如20个为一个单位。

    public static void addCustomers(){

            Session session = HibernateUtil.getSession();

            Transaction trans = session.beginTransaction();

           

            for(int i = 0; i< 1000000000; i++){

                Customer customer = new Customer("sssg","12sss56","890","广州","sssss","sssssssi@qq.com");

                customer.setUserName("name"+(i+1));

                session.save(customer);

                if(i%20 == 0){

                    session.flush();

    session.clear();

    trans.commit();

                    trans = session.beginTransaction();

                }

            }

            trans.commit();

            HibernateUtil.closeSession();

        }

        3.2批量更新

        采用类似批量插入的方法,来完成批量的更新;或者是使用scroll()将返回的数据进行更新操作,从而充分利用游标所带来的性能优化:

    方法一:

    public static void updateCustomers(){

        Session session  = HibernateUtil.getSession();

        Transaction trans = session.beginTransaction();

       

        ScrollableResults customers = session.createQuery("from Customer").scroll();

       

        int count = 1;

        while(customers.next()){

            Customer customer = (Customer) customers.get(0);

            customer.setUserName("yang"+count);

           

            if(count%20 == 0){

                session.flush();

                session.clear();

                trans.commit();trans= session.beginTransaction();

            }

            count++;       

        }

        trans.commit();

        HibernateUtil.closeSession();

    }

    上面这些跟新是每一条更新就会执行一条SQL,效率比较低。HQL中可以支持批量更新和删除的

    update | delete from ClassName [where condition] 注意这里使用的是Class中的属性而不是数据库中表的列的名称

    public static void updateCustomerByHQL(){

        Session session = HibernateUtil.getSession();

        Transaction trans = session.beginTransaction();

       

        String hql = "update Customer c set c.userName = :newName";

        Query query = session.createQuery(hql);

        query.setString("newName", "yangtengfei");

        query.executeUpdate();

       

        trans.commit();

        HibernateUtil.closeSession();

    }

    YangTengfei

    2013.11.28

  • 相关阅读:
    java开发:分享一下百度ueditor和七牛的图片集成上传
    java开发:分享一下使用urlrewrite实现网址的个性访问
    javascript应用:页面解析list和map封装后的json数据
    JAVA开发:分享一些SpringMvc+Ibatis+spring的框架使用心得
    使用OLEDB读取excel和csv文件
    静态代码块、构造代码块
    序列化和反序列化
    windows下Mysql5.7.10免安装版配置
    form表单中的encType属性
    关于字符编码,你所需要知道的(ASCII,Unicode,Utf-8,GB2312…)
  • 原文地址:https://www.cnblogs.com/hbhzsysutengfei/p/3473213.html
Copyright © 2011-2022 走看看