<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    千里馬

    天馬行空

    Hibernate總結

    1,任何的計算機程序都是由指令和數據兩部分組成,持久化數據對于對于大多數程序,尤其是企業級應用程序,是必不可少的。數據的持久化,,也就是把數據保存起來,并且可以供程序獲取這些數據的全部和某一部分。對于java程序來說,有3個持久化數據的途徑:文本文件、對象的序列化和數據庫。
    文本持久化數據對于數據量少和數據結構單一的情況比較好。如果數據量大,由于IO的操作速度比內存的操作速度要慢得多,會造成很大的性能問題。另外,如果數據的結構太復雜,簡單的符號相隔 的形式實在難于滿足數據的粗去功能。
    對象的序列化可以滿足數據結構復雜的存取,但是還是很難解決數據量大的問題。而且,它也很難滿足大多數企業級程序所需要的檢索功能。
    關系數據庫是目前數據持久化最成熟的產品,也是java程序首選的數據持久化的解決方案。它能夠存取海量的數據,提供高性能的數據檢索功能,大多數的數據庫廠商也提供了java的jdbc驅動。但是,如果使用jdbc來操作數據庫,會有以下幾項不可避免的弊端:
    (1),數據操作的代碼量巨大。
    (2),重復勞動的裝填數據。
    (3),面向對象的思想和關系模型之間的沖突。
    2,Hibernate基礎:
      Hibernate是一個開放源代碼的對象關系映射框架,它對jdbc進行了輕量級的對象封裝,使得java程序員可以隨心所欲的使用面向對象編程思想來操作數據庫。Hibernate可以應用在任何使用jdbc的場合,既可以在普通的java程序中使用,也可以在javaweb 應用程序中使用,還可以在EJB容器中使用,完成數據持久化的任務,極大地減輕了程序員的數據層工作。
    Hibernate就好像在java程序和數據庫之間的一座橋梁,它提供了豐富的API供程序員使用,當程序員通過這些API操作數據對象的時候,Hibernate會自動完成于數據庫之間的數據同步,還有跨數據庫的作用。
    Hibernate的底層實現依然是jdbc,但是程序員已經看不到任何jdbc的影子了,它提供給開發者的是另外一套API。數據庫操作的基本單元是表格,而ORM技術操作的基本單元是實體對象,所有Hibernate持久化數的操作方式又是一種全新的模式。Hibernate的5個重要的接口:Session、SessionFactory、Configuration、Transaction和Query,他們同時也是Hibernate最核心的組成概念。
    (1),Session接口:負責執行被持久化對象的添加、刪除、查詢、修改操作,有點類似與jdbc的Connection和Statement,他代表了java程序與數據庫之間的一次交流。需要注意的是,Session對象時非線程安全的,一般來說,一個線程包含一個Session對象。
    (2),SessionFactory是產生Session的工廠類,他負責為java程序創建Session。一般來說,一個SessionFactory代表了一個數據源,當需要操作多個數據庫時,可以為每個數據庫制定一個SessionFactory。一般情況,一個項目通常只需要一個SessionFactory就行了。
    (3),Configuration接口負責Hibernate的配置工作,創建SessionFactory對象。在Hibernate的啟動過程中,Configuration類的實例定位映射文件的位置、讀取配置,然創建SessionFactory對象。
    (4)Transaction接口負責事務的相關操作,它代表的Hibernate的事務,本質上也是數據庫事務。Transaction是可選的,開發者也可以設計編寫自己的底層事務處理代碼。
    (5),Query接口負責各種數據查詢功能,他也可以使用Hibernate特有的HQL語言和SQL語言兩種方式。
     以上這5個API接口是幾乎所有Hibernate程序都會使用到的,也是程序員使用Hibernate進行開發的基礎。他們之間的關系大致是這樣的:首先,有Configuration獲取配置信息并做一些初始化的工作;接著,Configuration創建SessionFactory;再通過SessionFactory創建Session;然后程序就使用Session完成一般的添加、刪除、查詢、修改操作了;如果需要使用復雜一點的查詢功能,則可以通過Session獲取Query,執行查詢操作。如果需要使用事務Transaction,也是在Session的范圍內使用。
    3,使用Hibernate的一般步驟: 
      (1),Hibernate所需的jar文件盒配置文件。
           要使用Hibernate,首先,把Hibernate所需的jar文件存放到java程序的類加載路徑里面;另外就是準備好Hibernate的配置文件。
      手動搭建Hibernate開發環境:
     1》,賦值所需的jar文件到java程序的類加載路徑下,對于web應用程序則復制到“WEB-INF/lib”目錄下。
     2》,為java程序準備一個Hibernate配置文件。一般情況下,文件名:hibernate.cfg.xml,存放在類加載路徑下,對web應用程序則存放在“WEB-INF/classes”里面。hibernate.cfg.xml的主要配置就是SessionFactory,它包括數據庫連接URL、數據庫別名、包含的實體和其他一些Hibernate工具等信息。該配置文件的內容是和Configuration接口相對應的,往往的應用程序只有一哥這樣的配置文件。:
    <?xml version='1.0' encoding='UTF-8'?>
    <!DOCTYPE hibernate-configuration PUBLIC
              "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
              "

    <!-- Generated by MyEclipse Hibernate Tools.                   -->
    <hibernate-configuration>

    <session-factory>
           <!-- 數據庫別名 -->
        <property name="dialect">org.hibernate.dialect.MySQLDialect</property>
        <!-- JDBC連接URL -->
     <property name="connection.url">jdbc:mysql://localhost:3306/test</property>
     <!-- 數據庫用戶名 -->
     <property name="connection.username">root</property>
     <!-- 數據庫密碼 -->
     <property name="connection.password">123</property>
     <!-- 數據庫JDBC驅動類名 -->
     <property name="connection.driver_class">com.mysql.jdbc.Driver</property>
     <!-- 顯示sql語句 -->
      <property name="show_sql">true</property>
      <!-- 自動建表設置 -->
        <property name="hbm2ddl.auto">create</property>
        <!-- 需要與數據庫進行ORM映射的實體 -->
        <mapping resource="com/insigma/User.hbm.xml"/>
    </session-factory>

    </hibernate-configuration>
    對于Hibernate工具,指的是為了方便程序員的開發和調研,hibernate提供的是一些可選的功能,下面是三個常用的Hibernate工具:
      show_sql 讓hibernate把底層執行的sql語句打印在控制臺上。   <property name="show_sql">true</property>
      format_sql 自動格式化打印到控制臺上的sql語句           <property name="format_sql">true</property>
      hbm2ddl.auto 用于自動創建數據庫表。通過它,在Hibernate每次使用之前,他會更具實體及他們之間的關系自動創建表或更改表結構。                                           <property name="hbm2ddl.auto">create</property>
    (2),創建POJO實體:
       實體,是ORM技術范疇的一個重要概念,它代表兌現現實世界的某種事物的抽象模擬,例如,用戶、學生、動物等。實體是Hibernate的基本操作單元,在開發者眼里實體就是一個數據對象,而且該數據對象是需要保存到數據庫里的。
    Hibernate操作的實體是簡單的java對象,與EJB的實體bean不同,POJO實體不需要繼承任何類和實現任何接口,他就是一個最普通的java對象,它的定義方式和javabean優點類似,也需要包含一個公開的默認的無參構造方法,也是使用setter和getter方法訪問實體的屬性。
    實體代表的是一類事物,那么每個實體靠什么區分開呢?與數據庫表格的主鍵類似,,實體也有主鍵,而且必須有一個主鍵,Hibernate會根據主鍵的相等與否區別實體對象。另外主鍵是一般沒有業務意義的,他僅僅用來區分不同的實體對象,常用java.lang.Lang型來定義實體對象的主鍵的。
    (3),創建數據庫表:
          1》手動創建。
           2》通過對hibernate.cfg.xml的配置,自動創建實體對應的表格需要加上這樣的配置:   <property name="hbm2ddl.auto">create</property> 在Hibernate每次使用之前,他會更具實體及他們之間的關系自動創建表或更改表結構。  當然的他的底層實現還是需要用到create等DML語言的SQL語句。
    (4),映射配置文件:
      映射配置文件是指明實體與數據庫之間是如何映射的,他負責告訴Hibernate從java程序到數據庫應該怎樣保存數據,以及如何從數據庫取出數據到java程序里。一般情況下,一個實體就對應一個映射配置文件。實體之間的關系也是在配置文件中進行相應配置的。
    映射配置文件時采用XML格式,其內容大致是這樣的,在跟標簽<hibernate-mapping>里使用<class>標簽配置實體類,通過《class》標簽的name屬性指定實體的完整類名,table指定表名,在《class》標簽里,必須使用《id》配置實體的主鍵和生成策略,然后使用《property》標簽配置實體其他屬性的映射。另外,還有可能使用《many-to-one》《set》等標簽配置實體與其他實體的關系。
                                         映射配置文件常用的XML標簽及其使用介紹
    標簽                 屬性                           說明
    <class>              name                       實體類名
                        table                     實體對應的數據庫表名
    <id>               name                          實體的主鍵屬性名
                        column                       數據庫表的主鍵字段名,默認與name相同
    <generator>           class                   主鍵生成策略
    <property>            name                    實體的屬性名
                          column                       數據庫表的對應的字段名,默認與name相同
                           not-null                      是否為空,默認可以
                             unique                       是否唯一,默認否
                           length                         字段的最大長度
    <one-to-one>                                           一對一
    <many-to-one>                                           多對一
    <many-to-many>                                           多對多
    <set>                                                用來建立集合映射
    (5)使用Hibernate API 操作數據:
        一切準備就緒以后,就可以使用Hibernate提供給開發者的API的操作實體數據了。程序員使用到的主要接口和類都在org.hibernate包里。
    package com.insigma;

    import org.hibernate.HibernateException;
    import org.hibernate.Session;
    import org.hibernate.cfg.Configuration;
    public class HibernateSessionFactory {
    private static String CONFIG_FILE_LOCATION = "/hibernate.cfg.xml";
    private static final ThreadLocal<Session> threadLocal = new ThreadLocal<Session>();
    private  static Configuration configuration = new Configuration();   
    private static org.hibernate.SessionFactory sessionFactory;
    private static String configFile = CONFIG_FILE_LOCATION;
         static {
         try {
       configuration.configure(configFile);
       sessionFactory = configuration.buildSessionFactory();
      } catch (Exception e) {
       System.err
         .println("%%%% Error Creating SessionFactory %%%%");
       e.printStackTrace();
      }
        }
        private HibernateSessionFactory() {
        }
    public static Session getSession() throws HibernateException {
            Session session = (Session) threadLocal.get();
      if (session == null || !session.isOpen()) {
       if (sessionFactory == null) {
        rebuildSessionFactory();
       }
       session = (sessionFactory != null) ? sessionFactory.openSession()
         : null;
       threadLocal.set(session);
      }

            return session;
        }
    public static void rebuildSessionFactory() {
      try {
       configuration.configure(configFile);
       sessionFactory = configuration.buildSessionFactory();
      } catch (Exception e) {
       System.err
         .println("%%%% Error Creating SessionFactory %%%%");
       e.printStackTrace();
      }
     }
    public static void closeSession() throws HibernateException {
            Session session = (Session) threadLocal.get();
            threadLocal.set(null);

            if (session != null) {
                session.close();
            }
        }
     public static org.hibernate.SessionFactory getSessionFactory() {
      return sessionFactory;
     }
    public static void setConfigFile(String configFile) {
      HibernateSessionFactory.configFile = configFile;
      sessionFactory = null;
     }
     public static Configuration getConfiguration() {
      return configuration;
     }
    }
    從以上代碼基本可以看出,使用Hibernate的步驟與jdbc有些類似,大致可以分為6步:
    1》生成配置對象(Configuration)。通過調用Configuration的configure() 方法,用配置文件的設置創建配置對象,一般情況下,配置對象只需要一個。
    2》創建SessionFactory對象。有配置對象創建一個SessionFactory對象,它代表了一個數據源。他的作用有一點類似于jdbc的驅動管理器,用來打開Session。一般情況,SessionFactory對象也只需一個。
    3》代開session。Hibernate的Session代表了一次與數據庫的連接,程序員需要的大多數操作都需要通過它。Session自帶了一個緩存,無論是否利用Session進行數據的添加、刪除、等都要經過緩存。
    4》利用Session進行各種實體操作。保存一個實體對象,可以調用Session的save(),persist(),saveorupdate()方法。HIbernate首先把沒有主鍵的實體保存保存在緩存里,然后在事務提交或調用Session.flush()方法以后把實體數據同步到數據庫里。
    對于修改一個實體對象的數據,如果程序是在Session關閉之前修改的,無需調用任何方法。否則,可以調用Session的update(),merge()saveOrUpdate()方法,進行實體的重新保存。
    刪除實體簡單,直接調用Session的dele()方法即可。
    當需要查詢實體時,使用Session的get()和load()方法或通過Session.createQuery()產生Query對象,執行查詢語句。無論用什么方式得到的實體,都會首先放在Session緩存里。
    5》事務處理.一般來說,除了查詢之外,其他的實體操作都需要使用到事務。開始-》提交-》(異常)回滾
    6》關閉Session。與JDBC關閉數據庫一樣。Session的關閉會讓Hibernate及時的把緩存里的數據同步到數據庫中。
    4,ID生成策略:
     主鍵ID,是實體的唯一標示符,它與數據庫的主鍵相對應。主鍵對于Hibernate是至關重要的,例如當程序調用Session.saveOrUpdate()方法的時候,Hibernate會以主鍵標準去緩存里找實體對象是否存在。如果存在則執行更新操作,否則執行新增操作。所以,保證實體是主鍵的唯一是Hibernate許多的工作基礎。
    主鍵的生成策略需要在實體映射配置文件中指定:常用的ID生成策略有:native、increment、sequence、assigned、identify、hilo、foreign
    (1)native:根據數據庫本地的生成策略生成主鍵。例如,Oracle采用Sequence,Mysql和sqlserver采用identify,也就是將主鍵的生成工作交給數據庫完成,Hibernate不做任何管理。
    (2),increment:插入數據的時候Hibernate會給主鍵添加一個自增的主鍵,一個Hibernate實例就維護一個計數器,所以在多個實例運行的時候就不能使用這個方法。
    (3)Sequence調用數據庫的sequence來生成主鍵,要設定序列名,不然hibernate無法找到,一般針對oracle使用。
    (4)assigned插入數據的時候主鍵有程序自己添加,hibernate不做任何管理。
    (5),identify:自增字段功能。不適合Oracle
    (6),該策略稱作高低策略,它是保障生成的結果具有唯一性的算法。需要在數據庫中建立一張額外的表,默認的表明為 hibernate_unique_key,默認的字段為integer類型名稱為,next_hi也可以通過配置指定表名和字段名。
    (7),采用外鍵來生成主鍵,表的主鍵是其他表的外鍵,也就是用其他表的外鍵來生成自己的表的主鍵。該策略常用與一對一的映射關系。
    5,關系映射:關系映射指的是實體之間的關系與數據庫表之間的關系相互對應的過程。建立關系映射之后,當程序員操作這些實體以及與之有關聯的實體的時候,就可以吧關系的操作同步到數據庫中,數據庫則一般表現為外鍵的各種操作。
    三種映射關系:一對一、一對多,多對多
    6,繼承映射:
    繼承關系是面向對象思想的特有關系,而數據庫不存在繼承關系。如果要把程序里的繼承關系映射到數據庫,,就需要用主外鍵的關系模擬這種繼承關系。一般情況下,用Hibernate建立繼承關系的映射,可以有兩種解決方案,各有優點,應該根據不同的情況采用不同的映射策略。
    (1)單表實現:單表繼承映射的時候,只需要定義一個映射配置文件就行了。
      單表是實現繼承映射的優點在于:沒有任何的表連接,查詢的速度回相對較快,多臺查效率高。但是他把所有的數據都存放在一張表里,有可能導致表特別大,不利于后期維護,而且子類的屬性很多,可能會有很多的null值,所以單表實現繼承映射更適合數據量小,,屬性個數小或多臺查詢比較多的情況。
    (2)每個子類一張表實現:優點在于數據存儲的比較緊湊,當查詢某個子類數據時比較快。但是由于有很多的連接,不太適合多臺查詢,更適合側重操作某一類數據的情況。所以多表實現的繼承映射比較適合數據量大、子類屬性個數多或經常查詢某一子類的情況。
    7,實體對象的生命周期:
    實體。作為數據的一種裝載單元,他在Hibernate的管理過程中,回不斷的發生數據和狀態的變化。Hibernate不僅僅是一個ORM的API工具,他還是一個容器,他可以幫你管理實體對象的生命周期,這個容器就是Session的緩存。
    Hibernate實體對象的三種狀態:瞬時態、持久態、托管態。實體對象的狀態會隨著Hibernate的API的調用而發生變化,開發者也應該根據實體對象的狀態的不同而使用不同的API。
     瞬時態:有new語句開辟內存空間的心Jjava對象。如果沒有沒有變量對該對象進行引用,他將被java虛擬機回收。
    瞬時對象在內存孤立,它是攜帶信息的載體,不和數據庫的數據有任何的關聯關系。最大的特點沒有主鍵。在Hibernate中,可通過Session的save()或saveOrUpdte()等方法將瞬時對象和數據庫關聯,并將數據同步到數據庫中。此時該瞬時對象轉化為持久化對象。
    持久態:處于持久態的對象在數據庫中具有對應的記錄,并有一個持久化標志。如果是用Session的delete()方法,對應的持久對象,就變成瞬時對象,因數據庫中的對應數據已被刪除,該對象不再關聯數據庫中任何的記錄。當執行Session的close clear、evict方法之后,此時持久對象變成托管對象仍具有數據庫識別值。他已不再Hibernate持久層的管理之下了。持久對象具有兩個特點:具有主鍵且數據庫中肯定有響應的記錄。
    托管態:當與某持久對象關聯的Session被關閉之后,持久變脫托管。當托管對象被重新關聯到Session上時,轉變為持久。托管對象具有數據庫的識別值。可通過update,saveOrUpdate方法轉變為持久對象。特點:本質上和瞬時對象一樣,在沒有任何變量引用的時候,jvm會在適當的時候回收,但是擁有主鍵。
    8,Hibernate中的查詢功能:hibernate提供的實體查詢功能是非常強大的,他不僅可以完成一般sql可以完成的功能,還可以智能的幫助開發者完成一些工作,例如自動填充數據,關聯加載、跨數據庫實現分頁查詢等
    (1)用get()和load()方法獲取單個實體對象
            根據主鍵去查詢實體,是最常見也是最簡單的查詢。使用Hibernate非常簡單,只需要調用get()和load()方法即可。他們的參數列表相同,第一個是實體的類型或完整類名,第二個是主鍵。查詢得到的實體對象,都進入持久態。盡管兩種方法作用類似,但是意義卻有些不同。get是去數據庫獲取實體對象,沒有放回null而load()的意義在于把指定主鍵的實體對象加載到緩存里。如果沒有的話,Hibernate拋出ObjectNotFoundException異常。
    (2)HQL查詢語言
    HQL是Hibernate提供給開發者以面向對象的思想進行實體添加、刪除、等操作的查詢語言,他看起來和sql比較相似,但是它提供了更加豐富和靈活的查詢特性,同時也提供了面向對象的封裝。
    1,實體查詢:
    最簡單的實體查詢就是直接使用from加實體名。
    String hql=“from User”;
    List list=Session.CreateQuery(hql).list();
    HQL與標準SQl相似,也可以在HQl語句中使用where,并且可以再where字句中使用表達式、比較操作符、以及使用and、or連接不同查詢條件的組合。
    2,實體的更新和刪除。
    與sql優點類似
    開始事務
    String hql=“”;
    Query q=Session.CreateQuery(hql);
    int ret=q.executeUpdate();
    提交事務
    3,屬性查詢:
    有的時候,檢索數據并不需要獲得實體對應的全部數據,而只需檢索出實體對應的部分數據,這時就可以利用HQL的屬性查詢你技術:
    4,排序和分組:
    (1)order by子句
    與sql語句相似,HQL查詢語句也可以使用order by子句對查詢結果進行排序,并且可以通過asc和desc關鍵字指定排序方式。
    (2)group by 子句和統計查詢
    在HQl語句中同樣支持使用group by子句分組查詢。還支持group by子句結合聚集函數的分組統計查詢。大部分標準的聚集函數都可以在HQL語句中使用。
    5,參數綁定:
    Hibernate對動態參數綁定提供了豐富的支持,HQL也像JDBC的Preparedstatement一樣,也可以只用占位符實現參數動態綁定。而且提供了更豐富的特性。在Hibernate中共提供了3中參數綁定方式。
    (1)按參數名綁定。
     在HQl語言中,定義命名參數使用“:”開頭;
    (2)用?來定義參數的位置
    (3)setparameter()方法
    5,分頁查詢
    Hibernate實現分頁查詢的功能支持非常好,可以說程序員使用分頁查詢是傻瓜式的,簡單到了極致,只需通過調用兩個方法告訴Hibernate從哪行開始和最多的行數其他的細節就交給Hibernate了。
    6,延遲加載

    延遲加載是Hibernate關聯關系的實體對象默認的加載方式,延遲加載機制是為避免一些無謂的性能開銷而提出來的。所謂的延遲加載就是在真正需要數據的時候,才真正執行數據加載操作,可以簡單的理解為,只用在使用的時候,才發出sql語句進行查詢。
    延遲加載第一種保障性能的技術,不一定要使用。可以通過在映射文件里進行設置不使用延遲加載。

    posted on 2012-06-15 19:43 Mr Lee 閱讀(1293) 評論(0)  編輯  收藏


    只有注冊用戶登錄后才能發表評論。


    網站導航:
     

    My Links

    Blog Stats

    常用鏈接

    留言簿

    隨筆分類

    隨筆檔案

    文章檔案

    (hibernate)http://www.tkk7.com/dyllove98/archive/2012/05/12/377959.html

    搜索

    最新評論

    閱讀排行榜

    評論排行榜

    主站蜘蛛池模板: 久久亚洲精品无码aⅴ大香 | 亚洲中文字幕伊人久久无码| 亚洲中文字幕无码不卡电影| 亚洲理论精品午夜电影| 久久精品无码专区免费青青| 男女啪啪永久免费观看网站| 在线观看亚洲天天一三视| 亚洲国产超清无码专区| 国产成人精品免费视频大全| 又粗又大又黑又长的免费视频 | 亚洲国产成人久久精品99| 亚洲美女在线观看播放| 美女隐私免费视频看| 91久久精品国产免费直播| 最新国产AV无码专区亚洲 | 国产午夜不卡AV免费| 亚洲 小说区 图片区 都市| 亚洲午夜精品国产电影在线观看| 日韩a毛片免费观看| 亚洲精品动漫免费二区| 久久久亚洲欧洲日产国码二区| 国产在线观看免费视频软件| 一个人看的在线免费视频| 成人黄网站片免费视频| 亚洲AV成人一区二区三区AV| 1024免费福利永久观看网站| 免费中文字幕视频| 久久青草亚洲AV无码麻豆| 四虎影院在线免费播放| 亚洲娇小性xxxx色| 永久免费无码网站在线观看 | 日韩成人毛片高清视频免费看| 亚洲自偷自偷图片| 中文字幕av免费专区| 在线观看亚洲人成网站| 国产在线国偷精品产拍免费| 无人视频在线观看免费播放影院| 亚洲中文久久精品无码| 24小时免费看片| 国产精品亚洲二区在线| 国产亚洲精品无码成人|