




版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡(jiǎn)介
Hibernate框架介紹8Hibernate框架介紹第章本章內(nèi)容8.1
Hibernate簡(jiǎn)介8.2
Hibernate原理8.3Hibernate工作流程8.4Hibernate框架的配置過(guò)程8.5
Hibernate的關(guān)系映射8.6案例:人事管理系統(tǒng)數(shù)據(jù)庫(kù)8.1
Hibernate簡(jiǎn)介8.1Hibernate簡(jiǎn)介Hibernate是一個(gè)開放源代碼的ORM(ObjectRelationalMapping,對(duì)象關(guān)系映射)框架,它對(duì)JDBC進(jìn)行了非常輕量級(jí)的對(duì)象封裝,它將POJO與數(shù)據(jù)庫(kù)表建立映射關(guān)系,是一個(gè)全自動(dòng)的ORM框架,Hibernate可以自動(dòng)生成SQL語(yǔ)句,自動(dòng)執(zhí)行,使得Java程序員可以隨心所欲的使用對(duì)象編程思維來(lái)操縱數(shù)據(jù)庫(kù)。8.2Hibernate原理MVC全名是ModelViewController,是模型(model)-視圖(view)-控制器(controller)的縮寫,一種軟件設(shè)計(jì)典范,用一種業(yè)務(wù)邏輯、數(shù)據(jù)、界面顯示分離的方法組織代碼,將業(yè)務(wù)邏輯聚集到一個(gè)部件里面,在改進(jìn)和個(gè)性化定制界面及用戶交互的同時(shí),不需要重新編寫業(yè)務(wù)邏輯。在實(shí)際應(yīng)用場(chǎng)景中,各大企業(yè)公司根據(jù)實(shí)際需要,基于MVC編程模式設(shè)計(jì)了很多框架,現(xiàn)在WEB開發(fā)使用最多的、最流程的便是SSH框架,SSH框架就是Struts+Spring+Hibernate的一個(gè)集成框架,是目前較流行的一種Web應(yīng)用程序開源框架,其中Hibernate框架對(duì)持久層提供支持。如下圖1所示為一個(gè)典型的B/S三層架構(gòu)圖。8.2Hibernate原理展示層:提供用戶交互界面業(yè)務(wù)邏輯層:實(shí)現(xiàn)各種業(yè)務(wù)和邏輯數(shù)據(jù)訪問層:負(fù)責(zé)存放和管理應(yīng)用程序的持久化業(yè)務(wù)數(shù)據(jù)。>SSH框架的系統(tǒng)從職責(zé)上分為四層:表示層、業(yè)務(wù)邏輯層、數(shù)據(jù)持久層和域模塊層,以幫助開發(fā)人員在短期內(nèi)搭建結(jié)構(gòu)清晰、可復(fù)用性好、維護(hù)方便的Web應(yīng)用程序。8.2Hibernate原理Hibernate將JDBC進(jìn)行了很好的封裝。Hibernate的目標(biāo)是釋放開發(fā)者通常的與數(shù)據(jù)庫(kù)持久化相關(guān)的編程任務(wù)的95%。消除那些針對(duì)特定數(shù)據(jù)庫(kù)廠商的SQL代碼。那么Hibernate如何工作的?如下圖2所示,這主要從三個(gè)方面:8.2Hibernate原理圖8-2Hibernate工作原理8.2Hibernate原理連接數(shù)據(jù)庫(kù):通過(guò)hibernate.cfg.xml配置文件中的配置
提供用戶交互界面,在這個(gè)文件中定義了數(shù)據(jù)庫(kù)進(jìn)行連接所需要的信息,包括JDBC驅(qū)動(dòng)、用戶名、密碼、數(shù)據(jù)庫(kù)方言,Configuration類借助dom4j的XML解析器解析設(shè)置環(huán)境,然后使用這些環(huán)境屬性來(lái)生成SessionFactory。這樣這個(gè)sessionFactory生成的session就能成功獲得數(shù)據(jù)庫(kù)的連接。
操作數(shù)據(jù)庫(kù):對(duì)數(shù)據(jù)庫(kù)的寫操作包括保存、更新和刪除,當(dāng)保存一個(gè)POJO持久對(duì)象時(shí),觸發(fā)Hibernate的保存事件監(jiān)聽器進(jìn)行處理。Hibernate通過(guò)映射文件獲得對(duì)象對(duì)應(yīng)數(shù)據(jù)庫(kù)表名以及屬性所對(duì)應(yīng)的表中的列名,然后通過(guò)反射機(jī)制持久化對(duì)象(實(shí)體對(duì)象)的各個(gè)屬性,最終組織成向數(shù)據(jù)庫(kù)插入新對(duì)象的SQLinsert語(yǔ)句。調(diào)用了session.save()方法后,這個(gè)對(duì)象會(huì)標(biāo)識(shí)成持久化狀態(tài)存放在session中,對(duì)于表1-1SQL功能及包含的主要?jiǎng)釉~8.2Hibernate原理Hibernate來(lái)說(shuō)它就是一個(gè)持久化了的對(duì)象,但這個(gè)時(shí)候Hibernate還不會(huì)真正的執(zhí)行insert語(yǔ)句,當(dāng)進(jìn)行session的刷新同部或事務(wù)提交時(shí),Hibernate會(huì)把session緩存中的所有SQL語(yǔ)句一起執(zhí)行,對(duì)于更新、刪除操作也是采用類似的機(jī)制。然后,提交事務(wù)并事務(wù)提交成功后,這些寫操作就會(huì)被永久地保存進(jìn)數(shù)據(jù)庫(kù)中,所以,使用session對(duì)數(shù)據(jù)庫(kù)操作還依賴于Hibernate事務(wù)的處理。如果設(shè)置了二級(jí)緩存,那么這些操作會(huì)被同步到二級(jí)緩存中,Hibernate對(duì)數(shù)據(jù)庫(kù)最終操作也是依賴于底層JDBC對(duì)數(shù)據(jù)庫(kù)進(jìn)行。8.2Hibernate原理查詢數(shù)據(jù):Hibernate提供SQL
HQL
Criteria查詢方式。HQL是其中運(yùn)用最廣泛的查詢方式。用戶使用session.createQuery()方法以一條HQL語(yǔ)句為參數(shù)創(chuàng)建
Query查詢對(duì)象后,Hibernate會(huì)使用Anltr庫(kù)把HQL語(yǔ)句解析成JDBC可以識(shí)別的SQL語(yǔ)句,如果設(shè)置了查詢緩存,那么執(zhí)行
Query.list()時(shí),Hibernate會(huì)先對(duì)查詢緩存進(jìn)行查詢,如果查詢緩存不存在,再使用select語(yǔ)句查詢數(shù)據(jù)庫(kù)。8.3Hibernate工作流程
在使用Hibernate框架時(shí)候,通常會(huì)使用到下面5各主要接口:Configuration接口、SessionFactory接口、Session接口、Transaction接口和Query接口。通過(guò)這些接口可以對(duì)持久化對(duì)象進(jìn)行操作,還可以進(jìn)行事務(wù)控制。因此Hibernate的執(zhí)行工作流程離不開上面核心接口,主要步驟如下圖3所示。8.3Hibernate工作流程
8.3Hibernate工作流程(4)創(chuàng)建Transaction實(shí)例,即開啟一個(gè)事務(wù)。通過(guò)Session對(duì)象的beginTransaction()方法即可開啟一個(gè)事務(wù),利用這的開啟的事務(wù),便可以對(duì)數(shù)據(jù)庫(kù)進(jìn)行各種持久化操作。(5)利用Session對(duì)象通過(guò)增刪改查等方法對(duì)數(shù)據(jù)庫(kù)進(jìn)行各種持久化操作。(6)提交事務(wù)。將第(4)步打開的事務(wù)通過(guò)mit()方法,進(jìn)行事務(wù)的提交(7)關(guān)閉Session。斷開與數(shù)據(jù)庫(kù)的連接。(8)關(guān)閉SessionFactory。注意:Hibernate的事務(wù)不是默認(rèn)開啟的,如果盡行增刪改的操作,需要手動(dòng)開啟事務(wù)。如果只是進(jìn)行查詢操作,可以不開啟事務(wù)。8.3Hibernate的核心組件
在Hibernate框架使用過(guò)程中,用戶調(diào)用HibernateAPI去對(duì)持久化對(duì)象操作時(shí)候,使用最多的6個(gè)核心組件是:Configuration接口、SessionFactory接口、Session接口、Transaction接口、Query接口和Criteria接口。如圖8-4所示,Hibernate的核心組件關(guān)系。8.3Hibernate的核心組件
8.3Hibernate的核心組件8.3.1Configuration接口Configuration類負(fù)責(zé)管理Hibernate的配置信息,在應(yīng)用程序剛開始運(yùn)行加載Hibernate框架時(shí),首先Configuration類負(fù)責(zé)啟動(dòng)、加載、管理Hibernate的配置信息。再啟動(dòng)Hibernate過(guò)程中,Configuration首先確定Hibernate配置文件的位置,然后再讀取相關(guān)配置信息,最后創(chuàng)建唯一的一個(gè)SessionFactory實(shí)例。Configuration只存在于系統(tǒng)初始化階段,它將SessionFactory創(chuàng)建完成后,就完成了自己的使命。Hibernate通常會(huì)使用newConfiguration().configure()方式來(lái)創(chuàng)建實(shí)例,此種方式默認(rèn)會(huì)去src下讀取hibernate.cfg.xml配置文件,如果不想使用默認(rèn)路徑的配置文件,也可以指定路徑目錄的配置文件,將路徑以參數(shù)形式傳遞到configure()方法,如下面代碼: Configurationcfg=newConfiguration(); cfg.configure("xml文件位置");//讀取指定的主配置文件例如要想使用src下config文件夾下的hibernate.cfg.xml,只需要將文件位置加到configure()方法參數(shù)即可,如下面代碼: Configurationconfigure=newConfiguration().configure("/config/hibernate.cfg.xml");8.3.2SessionFactory接口
Configuration對(duì)象根據(jù)當(dāng)前的配置信息生成SessionFactory對(duì)象。SessionFactory接口負(fù)責(zé)Hibernate的初始化和建立Session對(duì)象,SessionFactory對(duì)象一旦構(gòu)造完畢,即被賦予特定的配置信息(SessionFactory對(duì)象中保存了當(dāng)前的數(shù)據(jù)庫(kù)配置信息和所有映射關(guān)系以及預(yù)定義的SQL語(yǔ)句。同時(shí),SessionFactory還負(fù)責(zé)維護(hù)Hibernate的二級(jí)緩存)。主要代碼如下:Configurationcfg=newConfiguration().configure();SessionFactorysessionFactory=cfg.buildSessionFactory();SessionFactory具有下面幾個(gè)特點(diǎn):(1)線程安全。它的同一個(gè)實(shí)例可供多個(gè)線程共享。(2)它是重量級(jí)的,不可以隨意創(chuàng)建和銷毀。8.3.2SessionFactory接口
由于SessionFactory有以上特點(diǎn),因此在實(shí)際項(xiàng)目開發(fā)過(guò)程中,為了防止開發(fā)者隨意實(shí)例化SessionFactory,通常采用SessionFactory的單例模式,即將SessionFactory對(duì)象放到一個(gè)類中,并且定為私有的成員,再定義一個(gè)公有的get成員方法來(lái)返回SessionFactory對(duì)象,如果需要SessionFactory對(duì)象時(shí)候,只需要調(diào)用這個(gè)公有的get方法,從而保證了對(duì)象的唯一性,如下面代碼:8.3.2SessionFactory接口
publicclassHibernateUtils{ //全局只需要一個(gè)SesssionFactory就可以了 privatestaticSessionFactorysessionFactory; //初始化session static{ Configurationcfg=newConfiguration(); sessionFactory=cfg.configure().buildSessionFactory(); } /** *獲取全局唯一SessionFactory *@returnsessionFactory */ publicstaticSessionFactorygetSessionFactory() { returnsessionFactory; } publicstaticSessionopennSession() { returnsessionFactory.openSession(); }}8.3.2SessionFactory接口
在上面代碼中,首先聲明一個(gè)私有靜態(tài)變量SessionFactory對(duì)象,然后定義兩個(gè)公有靜態(tài)方法:getSessionFactory()和opennSession(),分別用來(lái)獲取SessionFactory對(duì)象和Sesssion對(duì)象,這樣就保證了可以通過(guò)HibernateUtils.getSessionFactory()獲取到唯一的SessionFactory對(duì)象,并且通過(guò)HibernateUtils.opennSession()獲取session連接。8.3.3Session接口Session是應(yīng)用程序與數(shù)據(jù)庫(kù)之間交互操作的一個(gè)單線程對(duì)象,是Hibernate運(yùn)作的中心,所有持久化對(duì)象必須在session的管理下才可以進(jìn)行持久化操作,為持久化對(duì)象提供創(chuàng)建、增加、刪除、修改等操作功能。
創(chuàng)建SessionFactory對(duì)象后,就可以通過(guò)它來(lái)獲取Session實(shí)例。獲取Session實(shí)例有兩種方法,一種是通過(guò)openSession()方法,另一種是通過(guò)getCurrentSession()方法。如下面代碼所示://采用openSession方法創(chuàng)建session Sessionsession=sessionFactory.openSession(); //采用getCurrentSession方法創(chuàng)建session Sessionsession=sessionFactory.getCurrentSession();8.3.3Session接口這兩種方式創(chuàng)建session對(duì)象的區(qū)別:openSession方法獲取Session實(shí)例時(shí),SessionFactory直接創(chuàng)建一個(gè)新的Session實(shí)例,并且在使用完以后需要使用close方法進(jìn)行手動(dòng)關(guān)閉。getCurrentSession()方法創(chuàng)建Session實(shí)例會(huì)被綁定在當(dāng)前線程中,它在提交或者回滾時(shí)候回自動(dòng)關(guān)閉。Session是線程不安全,多個(gè)并發(fā)線程在操作一個(gè)session實(shí)例時(shí),就可能導(dǎo)致Session數(shù)據(jù)存取混亂,因此設(shè)計(jì)軟件架構(gòu)時(shí),應(yīng)該盡量避免多個(gè)線程共享一個(gè)Session實(shí)例。同時(shí)Session是輕量級(jí)的,因此創(chuàng)建和銷毀對(duì)象不需要消耗太多資源。Session有一些常用的方法。具體如下:獲取持久化對(duì)象的方法。get()和load()方法,例如通過(guò)Objectget(Classclazz,Serializablearg)方法可以獲取指定arg(主鍵)的持久化對(duì)象的記錄。如下面代碼:8.3.3Session接口
Sessionsession=sessionFactory.openSession(); Transactiontx=session.beginTransaction(); Useruser=(User)session.get(User.class,1);//獲取主鍵id為1的user對(duì)象 System.out.println(user.getName()); mit(); session.close();持久化對(duì)象更新、保存和刪除的方法。save(),update(),saveOrUpdate(),delete(),如下面代碼所示: Useruser=newUser(); user.setName("張三"); Sessionsession=sessionFactory.openSession();//8.3.3Session接口
打開session Transactiontx=session.beginTransaction();//開始事務(wù) session.save(user);//更新用戶 mit();//提交事務(wù) session.close();持久化對(duì)象的查詢方法:createQuery(),createSQLQuery(),createCriteria()。開啟事務(wù):beginTransaction(),要操作持久化對(duì)象就必須開啟和提交事務(wù),下面代碼開啟一個(gè)事務(wù): Transactiontx=session.beginTransaction();管理Session方法:isOpen(),flush(),clear(),evict(),close()等8.3.4Transaction接口Hibernate是對(duì)JDBC的輕量級(jí)對(duì)象封裝,Hibernate本身是不具備Transaction處理功能的,Hibernate的Transaction實(shí)際上是底層的JDBCTransaction的封裝,或者是JTA(JavaTransactionAPI)的封裝。該接口允許應(yīng)用等量齊觀定義工作單元,同時(shí)又可調(diào)用JTA或JDBC執(zhí)行事物管理。它的運(yùn)行與Session接口相關(guān),可調(diào)用Session的beginTransaction()方法生成一個(gè)Transaction實(shí)例。Transaction接口常用如下方法:commit()。提交相關(guān)聯(lián)的Session實(shí)例。rollback();撤銷事物操作。wasCommitted();事物是否提交。8.3.4Transaction接口Session執(zhí)行完成對(duì)持久化對(duì)象的操作后,要想讓這些操作起作用,就必須對(duì)事務(wù)進(jìn)行提交,使用Transaction接口的commit()方法進(jìn)行事務(wù)的提交,只有這樣才能真正地將數(shù)據(jù)操作同步到數(shù)據(jù)庫(kù)中,當(dāng)數(shù)據(jù)操作發(fā)生異常時(shí)候,需要使用rollback()方法進(jìn)行事務(wù)回滾,以避免數(shù)據(jù)發(fā)生錯(cuò)誤,因此在持久化操作后,就必須調(diào)用Transaction接口的commit()方法和rollback()方法,如果沒有開啟事務(wù),那么每個(gè)Session操作都相當(dāng)于一個(gè)獨(dú)立的操作。8.3.5Query接口Query接口是Hibernate的查詢接口,用于向數(shù)據(jù)庫(kù)查詢對(duì)象,以及控制執(zhí)行查詢的過(guò)程。Query實(shí)例包裝了一個(gè)HQL(HibernateQueryLanguage)查詢語(yǔ)句,HQL查詢語(yǔ)句和SQL查詢語(yǔ)句有些相似,但HQL查詢語(yǔ)句是面向?qū)ο蟮?,它引用類句及類的屬性句,而不是表句及表的字段句。HQL語(yǔ)句Criteria查詢對(duì)查詢條件進(jìn)行了面向?qū)ο蠓庋b,符合編程人員的思維方式,不過(guò)HQL(HibernateQueryLanguage)查詢提供了更加豐富的和靈活的查詢特性,因此Hibernate將HQL查詢方式立為官方推薦的標(biāo)準(zhǔn)查詢方式,HQL查詢?cè)诤wCriteria查詢的所有功能的前提下,提供了類似標(biāo)準(zhǔn)SQL語(yǔ)句的查詢方式,同時(shí)也提供了更加面向?qū)ο蟮姆庋b。完整的HQL語(yǔ)句形式如下:Select/update/delete……from……where……groupby……h(huán)aving……orderby……asc/desc8.3.5Query接口其中的update/delete為Hibernate3中所新添加的功能,可見HQL查詢非常類似于標(biāo)準(zhǔn)SQL查詢。例如要查詢User表中所有的用戶,就可以執(zhí)行下面代碼: StringHQL="FROMUser"; Queryquery=session.createQuery(HQL); List<User>list=query.list();其中session.createQuery("FROMUser")的”FROMUser”就是HQL語(yǔ)句,通過(guò)session.createQuery()方法就可以得到Query對(duì)象,然后調(diào)用list()方法就可以執(zhí)行查詢。這里是無(wú)條件查詢(即查詢所有User)。Query執(zhí)行流程Query具體在Hibernate框架中使用具體步驟,具體如下所示:獲取Hibernate中的Session對(duì)象編寫HQL語(yǔ)句調(diào)用session.createQuery()方法創(chuàng)建查詢Query對(duì)象如果Query包含參數(shù)則可以調(diào)用Query的setXxx()方法來(lái)設(shè)置參數(shù)調(diào)用Query對(duì)象的list()或者uniqueResult()方法執(zhí)行查詢8.3.5Query接口下面將在一個(gè)Person表中,利用Query接口查詢數(shù)據(jù),具體代碼如下所示: publicvoidqueryTest(){Useruser=newUser();Sessionsession=HibernateUtils.opennSession();
Queryquery=session.createQuery("fromUser");Listlist=query.list();for(inti=0;i<list.size();i++){user=(User)list.get(i);System.out.println(user.getId());System.out.println(user.getName());}}8.3.5Query接口從上面代碼可以知道,首先需要得到Session對(duì)象,然后調(diào)用session.createQuery()方法創(chuàng)建查詢對(duì)象,再使用query.list()方法進(jìn)行數(shù)據(jù)查詢,并且將查詢的數(shù)據(jù)放入List集合中,最后循環(huán)出查詢結(jié)果。這里首先插入三條數(shù)據(jù),因此這里在控制臺(tái)打印輸出了三個(gè)id和name,如下圖8-5所示,圖8-6顯示JUnit測(cè)試結(jié)果狀態(tài)。圖8-5Query對(duì)象查詢結(jié)果8.3.5Query接口
圖8-6JUnit測(cè)試結(jié)果注意:這里采用JUnit4測(cè)試運(yùn)行結(jié)果顯示出如上圖,這里JUnit測(cè)試出現(xiàn)一條綠條說(shuō)明測(cè)試通過(guò),如果出現(xiàn)暗紅色條,則表示測(cè)試失敗,有錯(cuò)誤。Query接口除了可以使用list()方法進(jìn)行全部數(shù)據(jù)查詢以外,還有一些其它常用的方法:Query的executeUpdate()方法用于更新或刪除語(yǔ)句。它常用于批量刪除或批量更新操作,它是Hibernate3.0版本的新特性,并且支持HQL語(yǔ)句。 Queryq=session.createQuery("deletefromUser");q.executeUpdate();//刪除對(duì)象8.3.5Query接口Query的setXXX()方法用于設(shè)置查詢語(yǔ)句中的參數(shù),針對(duì)不同數(shù)據(jù)類型的參數(shù),會(huì)有不同的set方法,它主有二種重載方法:1)setString(intposition,Stringvalue):用于設(shè)置HQL中“?”的值:其中position表示?位置,而value自然就是值。如下: Queryquery=session.createQuery("fromUseruserwhereuser.id>?andlike?");//生成一個(gè)Query實(shí)例query.setInteger(0,20);//設(shè)置第一個(gè)問號(hào)的值為20query.setString(1,"張%");//設(shè)置第二個(gè)問題的值為張%2)setString(StringparaName,Stringvalue);用于設(shè)置HQL中“:”后跟變量的值;其中paraName代表HQL中“:”后跟變量,value為該變量設(shè)置的值。如下: Queryquery=session.createQuery("fromUseruserwhereuser.id>:minIdand8.3.5Query接口like:userName");//生成一個(gè)Query實(shí)例query.setInteger("minId",2);//設(shè)置minId的值為2query.setString("userName","張%");//設(shè)置userName的值為張%uniqueResult()方法,該方法返回唯一的結(jié)果,使用該方法前,必須確保返回得結(jié)果具有唯一性。如下面代碼:
Query
query
=
session.createQuery("from
Student
s
where
s.id=?");
query.setString(0,
"2");
Student
student
=
(Student)query.uniqueResult();
//當(dāng)確定返回的實(shí)例只有一個(gè)或者null時(shí)
用uniqueResult()方法8.3.5Criteria接口
Criteria是一種比HQL更面向?qū)ο蟮牟樵兎绞?。Criteria是Hibernate的核心查詢對(duì)象,Criteria查詢又稱為QBC查詢(QueryByCriteria),它是Hibernate的另一種對(duì)象檢索方式。如下面有單代碼: Listlist=session.createCriteria(User.class) .add(Restrictions.like("name","張%")) .add(Restrictions.between("id",2,5)) .list();org.hibernate.Criteria接口表示特定持久類的一個(gè)查詢。Session是Criteria實(shí)例的工廠。通常使用Criteria對(duì)象查詢數(shù)據(jù)的主要步驟如下:獲得Hibernate的Session對(duì)象。通過(guò)Session的createCriteria()方法獲得Criteria對(duì)象。使用Restrictions的靜態(tài)方法創(chuàng)建Criteria查詢條件。Criteria的add()方法用于添加查詢條件,addOrder()進(jìn)行結(jié)果排序。執(zhí)行Criteria的list()或者uniqueResult()獲得結(jié)果。Criterion的實(shí)例可以通過(guò)Restrictions工具類來(lái)創(chuàng)建,Restrictions提供了大量的靜態(tài)方法,即QBC查詢常用的方法:如下面所示:8.3.5Criteria接口
Restrictions.eq-->equal,等于。Restrictions.allEq-->參數(shù)為Map對(duì)象,使用key/value進(jìn)行多個(gè)等于的比對(duì),相當(dāng)于多個(gè)Restrictions.eq的效果Restrictions.gt-->great-than>大于Restrictions.ge-->great-equal>=大于等于Restrictions.lt-->less-than,<小于Restrictions.le-->less-equal<=小于等于Restrictions.between-->對(duì)應(yīng)SQL的between子句Restrictions.like
-->對(duì)應(yīng)SQL的LIKE子句Restrictions.in-->對(duì)應(yīng)SQL的in子句Restrictions.and-->and關(guān)系Restrictions.or-->or關(guān)系Restrictions.isNull-->判斷屬性是否為空,為空則返回true
相當(dāng)于SQL的isnullRestrictions.isNotNull-->與isNull相反
相當(dāng)于SQL的isnotnullRestrictions.sqlRestriction-->SQL限定的查詢Order.asc-->根據(jù)傳入的字段進(jìn)行升序排序Order.desc-->根據(jù)傳入的字段進(jìn)行降序排序MatchMode.EXACT-->字符串精確匹配.相當(dāng)于"like'value'"MatchMode.ANYWHERE-->字符串在中間匹配.相當(dāng)于"like'%value%'"MatchMode.START-->字符串在最前面的位置.相當(dāng)于"like'value%'"MatchMode.END-->字符串在最后面的位置.相當(dāng)于"like'%value'"8.3.5Criteria接口
下面通過(guò)一個(gè)Criteria查詢的例子來(lái)看一下Restrictions進(jìn)行查詢條件設(shè)置、排序等操作的主要代碼:
@Test publicvoidcriteriaTest(){ Sessionsession=sessionFactory.openSession();//打開session Transactiontx=session.beginTransaction();//開始事務(wù) List<User>list=session.createCriteria(User.class) //查詢條件設(shè)置為姓名為張三 .add(Restrictions.eq("name","張三")) //設(shè)置查詢條件為id>1的 .add(Restrictions.gt("id",1)) //按照ID的降序進(jìn)行排序 .addOrder(Order.desc("id")) .list(); for(Useru:list){ System.out.println(u); } mit();//提交事務(wù) session.close();}8.3.5Criteria接口
通過(guò)Criteria的靜態(tài)方法進(jìn)行查詢條件的設(shè)置,最后顯示姓名=為張三,id大于1,并且按id降序排序顯示,JUnit測(cè)試運(yùn)行結(jié)果如下所示。8.4Hibernate框架的配置過(guò)程
通過(guò)8.2節(jié)和8.3節(jié)的學(xué)習(xí),讀者已經(jīng)對(duì)Hibernate有了初步的了解,知道Hibernate的工作流程和核心接口,那么在實(shí)際Web開發(fā)過(guò)程中,如何使用Hibernate來(lái)對(duì)數(shù)據(jù)庫(kù)表進(jìn)行各種操作,本節(jié)將通過(guò)具體示例來(lái)進(jìn)行詳細(xì)說(shuō)明??偟膩?lái)說(shuō)Hibernate框架配置主要有下面四個(gè)步驟:導(dǎo)入相關(guān)Hibernate的jar包、創(chuàng)建數(shù)據(jù)庫(kù)及表、創(chuàng)建實(shí)體類(持久化類)、配置映射文件XX.hbm.xml、配置主配置文件hibernate.cfg.,xml、編寫數(shù)據(jù)庫(kù)操作(增刪改查)。8.4.1導(dǎo)入相關(guān)jar包
對(duì)于InnoDB存儲(chǔ)引擎的數(shù)據(jù)庫(kù)表而言,存在表空間的概念,InnoDB表空間分享表空間與獨(dú)享表空間。(1)共享表空間MySQL服務(wù)實(shí)例承載的所有數(shù)據(jù)庫(kù)的所有InnoDB表的數(shù)據(jù)信息、索引信息、各種元數(shù)據(jù)信息,以及事務(wù)的回滾(UNDO)信息,全部存放在共享表空間文件中。(2)獨(dú)享表空間如果將全局系統(tǒng)變量innodb_file_per_table的值設(shè)為ON(innodb_file_per_table的默認(rèn)值為OFF),則之后再創(chuàng)建InnoDB存儲(chǔ)引擎的新表時(shí),這些表的數(shù)據(jù)信息、索引信息將保存到獨(dú)享表空間文件中。8.4.1導(dǎo)入相關(guān)jar包
在Myeclipse中創(chuàng)建Java項(xiàng)目,8.4.1導(dǎo)入相關(guān)jar包新建Java項(xiàng)目,然后新建用于導(dǎo)入jar包的lib文件夾,將Hibernate的核心jar包和相關(guān)jar包導(dǎo)入lib后,然后將lib下的jar包全部“AddtoBuildPath”。這樣就可以將jar包導(dǎo)入項(xiàng)目。如圖8-8所示,導(dǎo)入的jar包中除了有Hibernate3的核心jar包以外還會(huì)有別的相關(guān)jar包,下面將對(duì)導(dǎo)入的jar包進(jìn)行簡(jiǎn)單說(shuō)明:Hibernate3.jar:Hibernate核心類庫(kù),必選包。commons-collections.jar:ApacheCommons包中的一個(gè)工具類,包含了一些Apache開發(fā)的集合類,功能比java.util.*強(qiáng)大,必選包。antlr-2.7..jar:語(yǔ)言轉(zhuǎn)換工,Hibernate利用它實(shí)現(xiàn)HQL到SQL的轉(zhuǎn)換
dom4j-1.6.1.jar:dom4j是一個(gè)Java的XMLAPI,類似于jdom,用來(lái)讀寫XML文件的8.4.1導(dǎo)入相關(guān)jar包javassist-3.12.0.GA.jar:一個(gè)開源的分析、編輯和創(chuàng)建Java字節(jié)碼的類庫(kù)jta-1.1.jar:標(biāo)準(zhǔn)Java事務(wù)(跨數(shù)據(jù)庫(kù))處理接口slf4j-api-1.6.1.jar:一個(gè)用于整合log4j的接口hibernate-jpa-2.0-api-1.0.0.Final.jar:JPA接口開發(fā)包log4.j-1.2.9.jar:
log4j庫(kù),Apache的日志工具
mysql-connector-j-8.2.0.jar:是jdbc的mysql8.2.0版本數(shù)據(jù)庫(kù)驅(qū)動(dòng)程序從上面可以看出,除了Hibernate3的核心JAR和JPA(JavaPersistenceAPI)接口開發(fā)包外,由于Hibernate并沒有提供對(duì)日志的實(shí)現(xiàn),所以需要log4和slf4j開發(fā)包整合Hibernate的日志系統(tǒng)到log4j。8.4.2創(chuàng)建數(shù)據(jù)庫(kù)及表本書中使用的數(shù)據(jù)庫(kù)是開源數(shù)據(jù)庫(kù)MySQL8.2.0。新建一個(gè)名為hibernateDemo的數(shù)據(jù)庫(kù),在此數(shù)據(jù)庫(kù)中創(chuàng)建一張t_student的表,主要SQL語(yǔ)句如下面所示:mysql>createdatabasehibernateDemodefaultcharactersetutf8;QueryOK,1rowaffected(0.03sec)mysql>usehibernateDemoDatabasechangedmysql>createtablet_student(idintprimarykeyauto_increment,namevarchar(20),ageint);QueryOK,0rowsaffected(0.13sec)8.4.2創(chuàng)建數(shù)據(jù)庫(kù)及表
查看數(shù)據(jù)表t_student的表結(jié)構(gòu)如下圖8-9所示:8.4.3創(chuàng)建實(shí)體類(持久化類實(shí)體類即Hibernate中的持久化類,即用來(lái)實(shí)現(xiàn)業(yè)務(wù)問題實(shí)體的類。持久化顧名思義就是把緩存中的東西放到數(shù)據(jù)庫(kù)中使之持久,對(duì)于需要持久化的對(duì)象,它的生命周期分為三個(gè)狀態(tài):臨時(shí)狀態(tài):剛剛用new語(yǔ)句創(chuàng)建,沒有被持久化,不處于session的緩存中,處于臨時(shí)狀態(tài)的java對(duì)象被稱為臨時(shí)對(duì)象。持久化狀態(tài):已經(jīng)被持久化,加入到session的緩存中,處于持久化的java對(duì)象被稱為持久化對(duì)象。游離狀態(tài):已經(jīng)被持久化,但不處于session的緩存中,處于游離狀態(tài)的java對(duì)象被成為游離對(duì)象。持久化類具有下面幾個(gè)特征:持久化對(duì)象和數(shù)據(jù)庫(kù)中的相關(guān)記錄對(duì)應(yīng)Session在清理緩存時(shí),會(huì)根據(jù)持久化對(duì)象的屬性變化來(lái)同步更新數(shù)據(jù)庫(kù)Session的save()方法把臨時(shí)狀態(tài)變?yōu)槌志没癄顟B(tài)Session的update(),saveOrUpdate()和lock()方法使游離狀態(tài)變?yōu)槌志没癄顟B(tài)8.4.3創(chuàng)建實(shí)體類(持久化類
持久化類實(shí)際上就是需要被Hibernate持久化到數(shù)據(jù)庫(kù)中的類。持久化類符合JavaBean的規(guī)范,包含一些屬性,以及與之對(duì)應(yīng)的getXXX()和setXXX()方法。在本項(xiàng)目中就創(chuàng)建了一個(gè)名為Student(對(duì)應(yīng)數(shù)據(jù)庫(kù)表的t_student)的實(shí)體類,該類有3個(gè)屬性:id,name,age分別對(duì)應(yīng)于表t_student中的3個(gè)字段,以及相應(yīng)的getter和setter方法,Student.java代碼如下所示:packagecn.hibernate.demo;publicclassStudent{ /* *student實(shí)體 */privateintid;privateStringname;privateintage;publicintgetAge(){ returnage;}8.4.3創(chuàng)建實(shí)體類(持久化類publicvoidsetAge(intage){ this.age=age;}publicintgetId(){ returnid;}publicvoidsetId(intid){ this.id=id;}publicStringgetName(){ returnname;}publicvoidsetName(Stringname){ =name;}publicStringtoString(){ returnname+":"+id+":"+age; }}8.4.4配置映射文件
通過(guò)前面8.4.3創(chuàng)建了實(shí)體類,實(shí)體類以及實(shí)體類的屬性與數(shù)據(jù)表一一對(duì)應(yīng),那么Hibernate框架中就要指出這種一一對(duì)應(yīng)關(guān)系:如哪一個(gè)實(shí)體類與哪一張表對(duì)應(yīng),類中的哪個(gè)屬性與表中的哪個(gè)字段進(jìn)行對(duì)應(yīng),這些都需要在映射文件中指出。通常在使用Hibernate框架中將會(huì)創(chuàng)建一個(gè)XX.hbm.xml的映射文件,其中XX名和實(shí)體類名保持一致,這樣可以很清楚地知道映射文件是哪個(gè)實(shí)體類的映射文件。本示例中就在實(shí)體類所在包下創(chuàng)建一個(gè)Student.hbm.xml文件,如下所示:<?xmlversion="1.0"?>8.4.4配置映射文件
<!DOCTYPEhibernate-mappingPUBLIC"-//Hibernate/HibernateMappingDTD3.0//EN""/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mappingpackage="cn.hibernate.demo"><!-- class屬性:實(shí)體類 table屬性:哪個(gè)表,可以省略,如果不寫表名默認(rèn)就是類的簡(jiǎn)單名稱,一般都會(huì)寫--><classname="Student"table="t_student"><idname="id"type="int"column="id"><!--主鍵生成策略--><generatorclass="native"/></id><!--普通屬性(數(shù)據(jù)庫(kù)中的值類型)--><propertyname="name"type="string"column="name"/><propertyname="age"type="int"column="age"/></class></hibernate-mapping>8.4.4配置映射文件
根據(jù)上面的XML配置文件,將對(duì)本XML配置文件中出現(xiàn)的一些主要節(jié)點(diǎn)進(jìn)行簡(jiǎn)單說(shuō)明:class節(jié)點(diǎn):用于配置一個(gè)實(shí)體類的映射信息,其中name屬性是表示這個(gè)實(shí)體的類名,table屬性表示這個(gè)實(shí)體類對(duì)應(yīng)的數(shù)據(jù)庫(kù)的表名。id節(jié)點(diǎn):用于定于實(shí)體類的標(biāo)識(shí)屬性對(duì)應(yīng)于數(shù)據(jù)表中的列,這里即表的主鍵<generator>子節(jié)點(diǎn)用于指定主鍵生成策略,這里一般都會(huì)選擇nativeproperty子節(jié)點(diǎn):用于映射普通屬性。其中name屬性對(duì)應(yīng)實(shí)例類的屬性,type屬性表示其屬性類型,column代表數(shù)據(jù)表中的普通字段(除主鍵外其他字段)8.4.5配置主配置文件Hibernate的映射文件是標(biāo)識(shí)持久化類和數(shù)據(jù)庫(kù)表的對(duì)應(yīng)關(guān)系,可以讓應(yīng)用程序通過(guò)映射文件找到持久化類和數(shù)據(jù)表的對(duì)應(yīng)關(guān)系,那么主配置文件hibernate.cfg.xml主要是用來(lái)配置數(shù)據(jù)庫(kù)連接以及Hibernate運(yùn)行時(shí)所需要的各個(gè)屬性的值,就像JDBC的配置文件perties那樣。在本示例項(xiàng)目的src下創(chuàng)建名稱為hibernate.cfg.xml的主配置文件,如下所示:8.4.5配置主配置文件
<!DOCTYPEhibernate-configurationPUBLIC "-//Hibernate/HibernateConfigurationDTD3.0//EN" "/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration> <session-factoryname="mark"> <!--配置數(shù)據(jù)庫(kù)信息--> <propertyname="dialect">org.hibernate.dialect.MySQLDialect</property> <propertyname="connection.driver_class">com.mysql.jdbc.Driver</property> <propertyname="connection.url">jdbc:mysql://localhost:3306/hibernateDemo</property> <propertyname="connection.username">root</property> <propertyname="connection.password">root</property>
<!--其他配置--> <propertyname="hibernate.format_sql">true</property> <propertyname="show_sql">true</property> <!--hibernate.hbm2ddl.auto:如果沒有表自動(dòng)創(chuàng)建表, create先刪除,再創(chuàng)建 update如果表不存在就創(chuàng)建,不一樣就更新,一樣就什么都不做 create-drop:初始化創(chuàng)建表,sessionFactory執(zhí)行close()時(shí)候刪除表 validate:驗(yàn)證表結(jié)構(gòu)是否一致,如果不一致就拋出異常 --> <propertyname="hibernate.hbm2ddl.auto">update</property> <!--導(dǎo)入映射關(guān)系文件--> <mappingresource="cn/hibernate/demo/Student.hbm.xml"/> </session-factory></hibernate-configuration>8.4.5配置主配置文件
添加數(shù)據(jù)測(cè)試方法saveTest運(yùn)行結(jié)果如下圖8-10所示:圖8-10saveTest保存數(shù)據(jù)測(cè)試運(yùn)行結(jié)果8.4.5配置主配置文件
使用Hibernate框架查詢數(shù)據(jù),主要有幾種方式:一種get和load方式,一種是使用Query對(duì)象和HQL語(yǔ)句進(jìn)行查詢,一種使用criteria進(jìn)行查詢。1)get和load方法獲取查詢數(shù)據(jù)表中的某條數(shù)據(jù),可以通過(guò)session的get方法,如需要獲取id=1的數(shù)據(jù),可按照下面代碼完成數(shù)據(jù)獲取功能,主要代碼如下面所示:8.4.5配置主配置文件@Test publicvoidtestGet() {
Sessionsession=sessionFactory.openSession(); Transactiontx=session.beginTransaction(); //獲取id為1的student對(duì)象 Studentstudent=(Student)session.get(Student.class,1); System.out.println(student.getName()); mit(); session.close(); }8.4.5配置主配置文件{ Configurationcfg=newConfiguration(); //讀取指定的主配置文件 cfg.configure("hibernate.cfg.xml"); //根據(jù)主配置文件生成session工廠 sessionFactory=cfg.buildSessionFactory(); } //添加操作 @Test publicvoidsaveTest() { //保存 Studentstudent=newStudent(); student.setName("李剛"); student.setAge(22); //打開session Sessionsession=sessionFactory.openSession(); //開始事務(wù) Transactiontx=session.beginTransaction(); //將數(shù)據(jù)存儲(chǔ)到數(shù)據(jù)表中 session.save(student); //提交事務(wù) mit(); //關(guān)閉session session.close(); }}8.4.5配置主配置文件
查詢數(shù)據(jù)表中session.get(Student.class,1)方法第一個(gè)參數(shù)表示獲取實(shí)體類的類型,第二個(gè)參數(shù)表示數(shù)據(jù)表主鍵值,這樣就可以索引到這條數(shù)據(jù),因此通過(guò)student實(shí)體對(duì)象的getName()方法就可以獲取到id為1的人的姓名,運(yùn)行結(jié)果如下圖8-11所示:8.4.5配置主配置文件圖8-11testGet方法查詢數(shù)據(jù)測(cè)試運(yùn)行結(jié)果從上面8-11運(yùn)行結(jié)果可以看到控制臺(tái)開始有幾行紅色字體的警告內(nèi)容,這是由于沒有配置log4j配置文件所顯示的,這會(huì)影響顯示結(jié)果。警告信息下面有一些Hibernate自動(dòng)生成的SQL語(yǔ)句,這是由于在主配置文件hibernate.cfg.xml中增加了顯示SQL語(yǔ)句和格式化SQL的配置信息,才會(huì)有這些SQL語(yǔ)句信息顯示出來(lái),最后一行才是真正的查詢結(jié)果。查詢還可以通過(guò)load()方法進(jìn)行查詢,使用load方式代碼和get幾乎一樣,就是將get方法該為load方法,其他都是一樣的。查詢主要代碼如下所示:8.4.5配置主配置文件
@Test publicvoidtestLoad() {
Sessionsession=sessionFactory.openSession(); Transactiontx=session.beginTransaction(); //獲取id為1的student對(duì)象 Studentstudent=(Student)session.get(Student.class,1); System.out.println(student.getName()); mit(); session.close(); }8.4.5配置主配置文件
運(yùn)行結(jié)果也和get()方法運(yùn)行結(jié)果一樣,如圖8-11所示。Session實(shí)例提供了get和load兩種加載數(shù)據(jù)方式,兩者主要區(qū)別是:load方式檢索不到的話會(huì)拋出org.hibernate.ObjectNotFoundException異常;get方法檢索不到的話會(huì)返回null。本質(zhì)上說(shuō):hibernate對(duì)于load方法認(rèn)為該數(shù)據(jù)在數(shù)據(jù)庫(kù)中一定存在,可以放心的使用代理來(lái)延遲加載,如果在使用過(guò)程中發(fā)現(xiàn)了問題,只能拋異常;而對(duì)于get方法,hibernate一定要獲取到真實(shí)的數(shù)據(jù),否則返回null。2)Query方式獲取查詢還可以通過(guò)Query
對(duì)象和HQL語(yǔ)句進(jìn)行查詢,HQL語(yǔ)句前面小節(jié)已經(jīng)提及到,為了查詢需要這里將示例的數(shù)據(jù)再添加幾條,然后再使用Query對(duì)象和HQL語(yǔ)句進(jìn)行條件查詢,代碼如下所示:8.4.5配置主配置文件
@Test publicvoidqueryTest(){Studentstudent=newStudent();Sessionsession=sessionFactory.openSession();Queryquery=session.createQuery("fromStudent");Listlist=query.list();for(inti=0;i<list.size();i++){student=(Student)list.get(i);System.out.println(student.getId());System.out.println(student.getName());}}8.4.5配置主配置文件
查詢完成后可以看到現(xiàn)在新的表中有6條數(shù)據(jù),前面幾行依然是Hibernate框架中自動(dòng)產(chǎn)生的SQL語(yǔ)句信息,最下面6行就是運(yùn)行結(jié)果,由于實(shí)體類中重寫了toString方法,因此最后顯示出是按照:name+id+age的形式進(jìn)行顯示,運(yùn)行結(jié)果如下圖8-12所示:8.4.5配置主配置文件Query查詢方式也可以添加查詢條件,如本示例中添加age大于25的查詢條件,主要代碼如下所示: @Test publicvoidqueryConTest(){Studentstudent=newStudent();Sessionsession=sessionFactory.openSession();Queryquery=session.createQuery("fromStudentstwherest.age>:age");query.setInteger("age",25);Listlist=query.list();for(inti=0;i<list.size();i++){student=(Student)list.get(i);System.out.println(student);}}8.4.5配置主配置文件
可以看出HQL語(yǔ)句查詢條件中需要添加查詢變量,這里Query查詢條件可以通過(guò)set的兩種方式來(lái)設(shè)置,設(shè)置方式前面小節(jié)講解query時(shí)候已經(jīng)提及到,這里不再贅述。運(yùn)行結(jié)果如下圖所示:8.4.5配置主配置文件
3)Criteria查詢Criteria查詢可以使用Restrictions類提供了查詢限制機(jī)制。它提供了許多靜態(tài)方法,以實(shí)現(xiàn)查詢限制。前面小節(jié)講解Criteria時(shí)候已經(jīng)提及,本示例主要演示查詢條件name為姓李的,id大于等于1,并且降序排列,最后顯示出查詢結(jié)果。主要代碼如下所示:8.4.5配置主配置文件
@Test publicvoidcriteriaTest(){ Sessionsession=sessionFactory.openSession();//打開session Transactiontx=session.beginTransaction();//開始事務(wù) List<Student>list=session.createCriteria(Student.class) //查詢條件設(shè)置為姓名為張三 .add(Restrictions.like("name","李%")) //設(shè)置查詢條件為id>1的 .add(Restrictions.ge("id",1)) //按照ID的降序進(jìn)行排序 .addOrder(Order.desc("id")) .list();
for(Studentu:list){ System.out.println(u); } mit();//提交事務(wù) session.close();}8.4.5配置主配置文件使用Criteria查詢結(jié)果如下圖所示:8.4.5配置主配置文件3.更新數(shù)據(jù)更新數(shù)據(jù)也可以通過(guò)Hibernate框架來(lái)完成,下面將t_student表中修改id=1的數(shù)據(jù),將其name和age字段值都進(jìn)行修改,主要代碼如下所示:@Test publicvoidtestUpdate() { //保存 Studentstudent=newStudent(); student.setId(1); student.setName("張紅"); student.setAge(28); //打開session Sessionsession=sessionFactory.openSession(); //開始事務(wù) Transactiontx=session.beginTransaction(); //將數(shù)據(jù)更新到數(shù)據(jù)表中 session.update(student); //提交事務(wù) mit(); //關(guān)閉session session.close(); }8.4.5配置主配置文件
從上面代碼可以看出update更新方法和save添加方法非常相像,只是通過(guò)session執(zhí)行的方法不一樣,save是添加新數(shù)據(jù),而update是對(duì)原有數(shù)據(jù)進(jìn)行更新操作。執(zhí)行結(jié)果如下圖8-15所示:8.4.5配置主配置文件刪除數(shù)據(jù)刪除數(shù)據(jù)表中的某條數(shù)據(jù)就要知道這條語(yǔ)句的主鍵id對(duì)應(yīng)的實(shí)體類對(duì)象,然后通過(guò)session.delete()方法來(lái)進(jìn)行數(shù)據(jù)的刪除,主要代碼如下所示: @Test publicvoiddeleteTest(){Sessionsession=sessionFactory.openSession();Transactiontx=session.beginTransaction();//開始事務(wù) Studentstudent=(Student)session.get(Student.class,1); session.delete(student);System.out.println(student); mit();//提交事務(wù) session.close();}8.4.5配置主配置文件
運(yùn)行結(jié)果下圖8-16所示:8.4.5配置主配置文件
從Hibernate的SQL語(yǔ)句信息可以看出先執(zhí)行了查詢,然后又執(zhí)行了刪除語(yǔ)句,最后在數(shù)據(jù)庫(kù)中查詢結(jié)果如圖8-17所示:8.4.5配置主配置文件刪除語(yǔ)句也可以通過(guò)創(chuàng)建新的實(shí)體實(shí)例進(jìn)行修改,如果將代碼get()查詢方法去掉,通過(guò)id得到實(shí)例化Student實(shí)體,也可以同樣刪除相應(yīng)id的語(yǔ)句,如修改下面語(yǔ)句://Studentstudent=(Student)session.get(Student.class,1);Studentstudent=newStudent();student.setId(2); session.delete(student);8.4.5配置主配置文件通過(guò)id得到實(shí)例化Student實(shí)體,也可以同樣刪除相應(yīng)id的語(yǔ)句,如修改下面語(yǔ)句:通過(guò)上面的刪除語(yǔ)句,將id為2的Student數(shù)據(jù)從表中也刪除了,刪除后控制臺(tái)運(yùn)行結(jié)果如圖8-19所示,數(shù)據(jù)庫(kù)查詢結(jié)果如圖8-20所示。8.4.5配置主配置文件當(dāng)然也可以從用HQL語(yǔ)句進(jìn)行批量刪除操作,如下面刪除大于22歲的所有Student,就可以執(zhí)行下面代碼: @Test publicvoiddeleteHQLTest(){Sessionsession=sessionFactory.openSession();Transactiontx=session.beginTransaction();//開始事務(wù)Stringhql="deleteStudentwhereage>22";Queryquery=session.createQuery(hql);intref=query.executeUpdate();System.out.println(ref); mit();//提交事務(wù) session.close();}8.4.5配置主配置文件
運(yùn)行結(jié)果控制臺(tái)顯示如圖8-21所示:8.5Hibernate的關(guān)系映射
Hibernate框架實(shí)現(xiàn)了ORM(ObjectRelationMapping)思想,將關(guān)系型數(shù)據(jù)庫(kù)中的表數(shù)據(jù)映射成對(duì)象,并且在映射文件XX.hbm.xml中配置數(shù)據(jù)表與持久化(實(shí)體)對(duì)象的對(duì)應(yīng)關(guān)系,這樣即可以關(guān)系表之間的數(shù)據(jù)進(jìn)行同步,本節(jié)將對(duì)Hibernate的關(guān)聯(lián)關(guān)系映射進(jìn)行說(shuō)明。數(shù)據(jù)庫(kù)中多表存在三種關(guān)系,也就是系統(tǒng)設(shè)計(jì)中的三種實(shí)體關(guān)系:一對(duì)一,一對(duì)多,多對(duì)多關(guān)系。三種實(shí)體關(guān)系在實(shí)際開發(fā)中,一對(duì)一使用較少,大部分都是后兩種。1.一對(duì)多關(guān)系一對(duì)多的關(guān)系例如部門和員工之間的關(guān)系,以部門和員工為例,創(chuàng)建一對(duì)多關(guān)系的實(shí)體類,其中員工實(shí)體類(省略get和set方法)如下://員工實(shí)體類publicclassEmployee{privateIntegerid;privateStringname;privateDepartmentdepartment;}8.5Hibernate的關(guān)系映射在一對(duì)多關(guān)系中,對(duì)象模型中是在“一”的一端添加Set集合,包含“多”的一端。那么本示例就是在部門實(shí)體類中添加員工集合,部門的實(shí)體類如下://部門實(shí)體類publicclassDepartment{ privateIntegerid; privateStringname; privateSet<Employee>employee=newHashSet<Employee>();}8.5Hibernate的關(guān)系映射
映射文件也需要進(jìn)行相應(yīng)的配置,需要對(duì)部門實(shí)體類和員工實(shí)體類兩個(gè)實(shí)體進(jìn)行映射配置,在“多”的一端加入<many-to-onename="’一’的表名"class="’一’的實(shí)體類名"column="’一’的主鍵">,員工Employee.hbm.xml配置文件如下:<classname="Employee"table="employee"><idname="id"><generatorclass="native"/></id><propertyname="name"></property><!--department的屬性,表示多對(duì)一的關(guān)系class屬性:代表關(guān)聯(lián)的實(shí)體內(nèi)容column屬性:代表外鍵列,表示引用關(guān)聯(lián)對(duì)象的主鍵--><many-to-onename="department"class="Department"column="departmentId"></many-to-one></class>8.5Hibernate的關(guān)系映射上面的員工映射文件中class屬性代表實(shí)體類,table屬性代表數(shù)據(jù)庫(kù)表名。在一對(duì)多的關(guān)系中,“一”的一方配置文件需要增加<set>、<one-to-many>和<key>標(biāo)簽并配置“多”的一方信息,表示“一”的一方指向“多”的一方。部門Department.hbm.xml配置文件如下:<classname="Department"table="department"><idname="id"><generatorclass="native"/></id><setname="employee"inverse="false"cascade="delete"><keycolumn="departmentId"></key><one-to-manyclass="Employee"/></set></class>8.5Hibernate的關(guān)系映射上面的員工映射文件中class屬性代表實(shí)體類,table屬性代表數(shù)據(jù)庫(kù)表名。在一對(duì)多的關(guān)系中,“一”的一方配置文件需要增加<set>、<one-to-many>和<key>標(biāo)簽并配置“多”的一方信息,表示“一”的一方指向“多”的一方。部門Department.hbm.xml配置文件如下:<classname="Department"table="department"><idname="id"><generatorclass=
溫馨提示
- 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 消防安全合同管理規(guī)定
- 船舶制造材料供應(yīng)合同
- 新建住宅買賣合同備案流程
- 股權(quán)轉(zhuǎn)讓合同及相關(guān)權(quán)益轉(zhuǎn)讓協(xié)議
- 股權(quán)轉(zhuǎn)讓居間服務(wù)合同樣本
- 商鋪?zhàn)赓U合同參考模板
- 小班安全玩滑梯課件
- 創(chuàng)業(yè)企業(yè)的股權(quán)結(jié)構(gòu)設(shè)計(jì)考核試卷
- 方便食品的包裝設(shè)計(jì)與人機(jī)工程考核試卷
- 新材料新技術(shù)的巨大潛力探索未知的研究領(lǐng)域考核試卷
- 法規(guī)解讀丨2024新版《突發(fā)事件應(yīng)對(duì)法》及其應(yīng)用案例
- JGJ46-2024 建筑與市政工程施工現(xiàn)場(chǎng)臨時(shí)用電安全技術(shù)標(biāo)準(zhǔn)
- 肺炎的中醫(yī)護(hù)理方案
- 2024年世界職業(yè)院校技能大賽高職組“關(guān)務(wù)實(shí)務(wù)組”賽項(xiàng)參考試題庫(kù)(含答案)
- 河北美術(shù)出版社小學(xué)六年級(jí)下冊(cè)書法練習(xí)指導(dǎo)教案
- 五下音樂《美麗的家鄉(xiāng)(簡(jiǎn)譜、五線譜)》課件
- 2024年長(zhǎng)沙職業(yè)技術(shù)學(xué)院高職單招(英語(yǔ)/數(shù)學(xué)/語(yǔ)文)筆試歷年參考題庫(kù)含答案解析
- 轉(zhuǎn)學(xué)申請(qǐng)表、轉(zhuǎn)學(xué)證明
- (完整版)部編四年級(jí)語(yǔ)文下詞語(yǔ)表
- 高頻電子線路完整章節(jié)課件(胡宴如)
- 鋁擠壓設(shè)備日常巡檢保養(yǎng)記錄
評(píng)論
0/150
提交評(píng)論