Hibernate學習筆記②

一、實體類的編寫規則

      - JavaBean+屬性中必須有惟一值的屬性(對應數據庫表的字段)mysql

      - 實體類屬性不建議使用基本數據類型,建議使用基本數據類型對應的包裝類redis

               int - Integer   char - Character  其餘的都是首字母大寫 好比 double - Doublesql

      爲何這樣寫呢?舉例說 學生參加考試確定有字段int score 若是他得了0分,sroce = 0就好了,可是若是這個學生沒有參加考試,是沒有score = null的,用Integer就可使用 Interger score = null就能夠了。數據庫

二、主鍵生成策略

<generator class="生成策略"></generator>數組

可選值:increment  每次增加 1緩存

           identity【只能用在mysql中】session

           sequenen【只能用在oracle中】併發

           ※ native 【根據使用的數據庫 自動選擇用的生成器  經常使用】oracle

           ※ uuid    【生成32位惟一字符串】 Hibernate生成的不是任何一個(規範)版本的UUID,強烈不建議使用。
ide

          UUID是Universally Unique Identifier的縮寫,它是在必定的範圍內(從特定的名字空間到全球)惟一的機器生成的標識符。

三、CRUD操做

     save  添加

     get   根據id查詢

/*
         * @param arg0  返回的實體類的Class
         * @param arg1 查詢的id
         * */
        User user = session.get(User.class, 2);

     update  修改

     ① 先根據id查詢 返回對象

     ② 在使用對象的setter方法修改值

     ③ session.update(對象)

    修改也能夠用session.save(對象)實現,可是最好用update方法。    

    delete 刪除

    【經常使用】第一種方式:

          ① 使用session.get查,返回對象

          ② session.delete(對象)

    第二種方式:

         ①  實例化一個實體類,使用setter方法設置id爲要刪除的id

         ② 使用session.delete(對象)刪除

四、實體類狀態

  瞬時態   沒有id 和session也沒有關係 瞬時態的實體類通常作save操做

  持久態   有id值 與session有關聯   session.get出的實體類就是持久態

  託管態   有id值 與session沒有關聯 【不經常使用】  刪除的第二種方法裏面的實體類就是一個託管態實體類

另外一個重要的方法 saveOrUpdate 根據實體類的狀態執行不一樣的操做

    實體類爲瞬時態  ->  saveOrUpdate作添加操做

    實體類爲持久態  ->  saveOrUpdate作修改操做

    實體類爲託管態  ->  saveOrUpdate作修改操做【不經常使用】

五、Hibernate一級緩存

    緩存:放在內存中

    有一級緩存和二級緩存

    一級緩存特色:

  • 一級緩存默認是打開的
  • 使用範圍是session範圍【從建立session到關閉session的】
  • 一級緩存的存儲數據必須是持久態

     注意:二級緩存已經不使用了,使用redis替代二級緩存

驗證一級緩存的存在

User user = session.get(User.class, 2);
System.out.println(user.getUsername());
User user1 = session.get(User.class, 2);
System.out.println(user1.getUsername());

第一次查詢時執行SQL,第二次查詢時直接調用的緩存,並不執行SQL語句。

Hibernate: 
    select
        user0_.uid as uid1_0_0_,
        user0_.username as username2_0_0_,
        user0_.password as password3_0_0_,
        user0_.address as address4_0_0_ 
    from
        t_user user0_ 
    where
        user0_.uid=?
Dongfang
Dongfang

Hibernate一級緩存的特性

  • 持久態實體類改變數據時 自動修改【無需session.save或update】
  • 原理:當一級緩存中沒有持久態對象時會進行查詢,查詢後會放到一級緩存和以及對應的快照區【副本】中,當使用setter方法修改屬性值時候,會同時修改一級緩存進行修改,可是不會修改一級緩存對應的快照區的值。當事務提交時,hibernate會比較一級緩存與快照區的內容是否相同,若是不相同會將一級緩存的內容更新到數據庫中。

六、Hibernate事務操做

隔離性:避免事務併發問題的發生

不考慮隔離性會產生的問題:髒讀、不可重複讀、虛讀

=》解決辦法:設置事務隔離級別  repeatable read【mysql默認的事務隔離級別】

Hibernate中在hibernate.cfg.xml能夠設置隔離級別,不經常使用

hibernate事務規範寫法

事務要有提交也要有回滾。

代碼結構:

      try{

          //開啓事務  Transaction tx = session.beginTransaction()

       //提交事務  tx.commit()

       }

      catch{

           //回滾事務 tx.rollback()

   }

  finally{

          //關閉事務/*不管有沒有異常 都會被關閉*/

    tx.close();

        }

七、hibernate與Session綁定

做用:確保session是惟一的,不共享的

方法:將session與本地線程綁定

 

<!-- 配置session綁定本地線程 -->
<property name="current_session_context_class">thread</property>

 

而後在HibernateUtil中增長getCurrentSession方法

public static Session getCurrentSession()
    {
        return sessionFactory.getCurrentSession();
    }

此時返回的Session對象就是與線程綁定的Session對象。

此時不須要手動關閉session,由於與本地session綁定了。

八、Hibernate API - 查詢

  • Query
  • Criteria
  • SQLQuery

(1)Query對象

  • 寫HQL語句,不寫SQL
  • HQL操做的是實體類

e.g. 查詢全部的HQL: from 實體類的名稱

//建立Query對象
Query query = session.createQuery("from User");
List<User> userlist = query.list();
            
for(User user : userlist)
{
   System.out.println(user.getUsername());
}

(2)Criteria對象

   不須要寫語句,直接調用方法便可。

Criteria c = session.createCriteria(User.class);
            List<User> userlist = c.list();
            for(User user : userlist)
                {
                    System.out.println(user.getUsername());
                }
session.createCriteria(User.class); 提示是過期的方法

(3)SQLQuery對象

SQLQuery sqlquery = session.createSQLQuery("select * from t_user");
List
<Object[]> list = sqlquery.list(); //默認返回的是數組的形式

讓返回的list的每部分爲實體類對象

SQLQuery sqlquery = session.createSQLQuery("select * from t_user");
sqlquery.addEntity(User.class);
List<User> list = sqlquery.list();

經過設置addEntity來達到返回的是實體類的對象

上面的方法提示所有過期

相關文章
相關標籤/搜索