Hibernate在初始化的時候,默認按照配置為表預定義insert,delete,update,select(by id)的SQL語句放在session中,其中insert,update,select操作都是對表的所有字段操作.如果在一個表有很多字段的時候,在做初次inser的時候有比較多的字段為空值,或者經常update某少部分字段,應該在配置文件的<class>元素上將dynamic-insert和dynamic-update設置為true.其默認值都為false.
如有這樣一張表:
create table hbtest(id int,val1 varchar2(100),val2 varchar2(100));
1,在 dynamic-insert沒有設置的時候
<class name="com.test.hb.dynamicupdate.Hbtest" table="HBTEST"> Hbtest tbo = new Hbtest(); tbo.setId(new Integer(2)); tbo.setVal1("val1"); sessionFactory.getCurrentSession().save(tbo);
某些字段為空做insert,hibernate會用全字段的insert sql語句,如下:
insert into HBTEST(VAL1, VAL2,ID) values(?, ?,?)
2,將dynamic-insert設置為true,同樣的保存,hibernate會動態生成SQL語句,沒有值的字段不會出現在insert語句中.
<class name="com.test.hb.dynamicupdate.Hbtest" dynamic-insert="true" table="HBTEST"> insert into HBTEST(VAL1, ID) values(?, ?)
3,在 dynamic-update沒有設置的時候
Hbtest tbo = (Hbtest) sessionFactory.getCurrentSession().load(Hbtest.class,new Integer(1)); tbo.setVal1("valXX"); tx.commit();
只更新部分字段,hibernate仍然對所有字段做更新:
update HBTEST set VAL1=?,VAL2=? where ID=?
4,同樣的操作如果把設置為true的話,sql語句只包含更新的字段:
update HBTEST set VAL1=? where ID=?
<class name="com.test.hb.dynamicupdate.Hbtest" dynamic-insert="true" dynamic-update="true" table="HBTEST">
5,Hibernate這種動態SQLupdate的特性是利用在對象從數據庫加載到hibernate session的時候保存了一份快照,做更新的時候與這個快照做比較,只更新改動過的值.
所以下面這種情況就會用全部字段進行更新:,不設值的字段會被更新成null.
Hbtest tbo = new Hbtest(); tbo.setId(new Integer(1)); tbo.setVal1("val1ZZZ"); sessionFactory.getCurrentSession().update(tbo);
這種情況應該利用Hibernate提供的對SQL的支持,用SQL做更新操作.