引用自他處,表示感謝!
現在假設有一個Student類,内有id,name,age屬性
String hql = "from Student s";
按照以前的做法,我們通常是
Query query = session.createQuery(hql);
或者要按照條件檢索的話.
String hql = "from Student s where s.name like '王%'"
Query query = session.createQuery(hql);
不用HQL而使用QBC的話,那麼代碼為:
Criteria criteria =session.createCriteria(Student.class);
Criterion criterion = Expression.like("name","王%");
這樣還看不出來.那我們把檢索條件加上年齡為22.
HQL:
String hql = "from Student s where s.name like '王%' and s.age= 22 ";
Query query = session.createQuery(hql);
List list = query.list();
QBC:
Criteria criteria =session.createCriteria(Student.class);
Criterion criterion1 = Expression.like("name","王%");
Criterion criterion2 = Expression.eq("age",newInteger(22));
criteria.add(criterion1).add(criterion2);
List list = criteria.list();
看上去煩瑣很多.但是做過項目的人都知道,當一個子產品業務邏輯發生改變的時候,往往要重寫sql,最煩也是最讨厭的就是拿着别人的hql或者sql,兩眼瞪的溜園找到底要修改什麼地方呢?
如果使用QBC大大的增加了代碼的可讀性,以及可維護性.
需要注意的是null值
比如我們要查找姓名為null的Student對象時應該這麼寫
Criteria criteria =session.createCriteria(Student.class);
Criterion criterion = Expression.isNull("name");
criteria.add(criterion).list();
以及使用between...and的時候
Criteria criteria =session.createCriteria(Student.class);
Criterion criterion1 = Expression.ge("age",new Integer(20));//下限
Criterion criterion2 = Expression.le("age",new Integer(25));//上限
//這裡也可以把上述兩個條件添加到第三個條件裡
Criterion criterion3 =Expression.and(criterion1,criterion2);
criteria.add(criterion3).list();
相當于from Student s where s.age between 20 and 25
等同于from Student s where s.age >= 20 and s.age <=25
下面是就HQL和QBC常用的查詢條件做的比較
表達式含義 HQL QBC
大于等于 >= Expression.ge()
大于 > Expression.gt()
小于等于 <= Expression.le()
小于 < Expression.lt()
等于 = Expression.eq()
不等于 <>或者!= Expression.ne()
為空 is null Expression.isNull()
不為空 is notnull Expression.isNotNull()
在指定範圍内 betweenand Expression.between()
不在指定範圍 not betweenand Expression.not(Expression.between())
屬于某個集合 in Expression.in()
不屬于某個集合 notin Expression.not(Expression.in())
與 and Expression.and()
或 or Expression.or()
非 not Expression.not()
模糊查詢 like Expression.like
1、建立一個Criteria執行個體 net.sf.hibernate.Criteria這個接口代表對一個特定的持久化類的查詢。Session是用來制造Criteria執行個體的工廠。
Criteria crit = sess.createCriteria(Cat.class);
crit.setMaxResults(50);
List cats = crit.list();
2、縮小結果集範圍 一個查詢條件(Criterion)是net.sf.hibernate.expression.Criterion接口的一個執行個體。類net.sf.hibernate.expression.Expression定義了獲得一些内置的Criterion類型。
List cats = sess.createCriteria(Cat.class)
.add( Expression.like("name", "Fritz%") )
.add( Expression.between("weight", minWeight, maxWeight))
.list();
表達式(Expressions)可以按照邏輯分組.
List cats = sess.createCriteria(Cat.class)
.add( Expression.like("name", "Fritz%") )
.add( Expression.or( Expression.eq( "age", new Integer(0) ), Expression.isNull("age")))
.list();
List cats = sess.createCriteria(Cat.class)
.add( Expression.in( "name",new String[]{"Fritz","Izi","Pk"}))
.add( Expression.disjunction()
.add( Expression.isNull("age") )
.add( Expression.eq("age", new Integer(0) ) )
.add( Expression.eq("age", new Integer(1) ) )
.add( Expression.eq("age", new Integer(2) ) ) ) )
.list();
有很多預制的條件類型(Expression的子類)。有一個特别有用,可以讓你直接嵌入SQL。
List cats = sess.createCriteria(Cat.class)
.add( Expression.sql("lower($alias.name) like lower(?)", "Fritz%", Hibernate.STRING))
.list();
其中的{alias}是一個占位符,它将會被所查詢實體的行别名所替代。(原文:The {alias} placeholder with be replaced by the row alias of the queried entity.)
3、對結果排序 可以使用net.sf.hibernate.expression.Order對結果集排序.
List cats = sess.createCriteria(Cat.class)
.add( Expression.like("name", "F%")
.addOrder( Order.asc("name"))
.addOrder( Order.desc("age"))
.setMaxResults(50)
.list();
4、關聯(Associations) 你可以在關聯之間使用createCriteria(),很容易地在存在關系的實體之間指定限制。
List cats = sess.createCriteria(Cat.class)
.add( Expression.like("name", "F%")
.createCriteria("kittens")
.add( Expression.like("name","F%")
.list();
注意,第二個createCriteria()傳回一個Criteria的新執行個體,指向kittens集合類的元素。 下面的替代形式在特定情況下有用。
List cats = sess.createCriteria(Cat.class)
.createAlias("kittens", "kt")
.createAlias("mate", "mt")
.add(Expression.eqProperty("kt.name", "mt.name"))
.list();
(createAlias())并不會建立一個Criteria的新執行個體。) 請注意,前面兩個查詢中Cat執行個體所持有的kittens集合類并沒有通過criteria預先過濾!如果你希望隻傳回滿足條件的kittens,你必須使用returnMaps()。
List cats = sess.createCriteria(Cat.class)
.createCriteria("kittens", "kt")
.add( Expression.eq("name", "F%") )
.returnMaps()
.list();
Iterator iter = cats.iterator();
while ( iter.hasNext())
{
Map map = (Map) iter.next();
Cat cat = (Cat) map.get(Criteria.ROOT_ALIAS);
Cat kitten = (Cat) map.get("kt");
}
5、動态關聯對象擷取(Dynamic association fetching) 可以在運作時通過setFetchMode()來改變關聯對象自動擷取的政策。
List cats = sess.createCriteria(Cat.class)
.add( Expression.like("name", "Fritz%") )
.setFetchMode("mate", FetchMode.EAGER)
.list();
這個查詢會通過外連接配接(outer join)同時獲得 mate和kittens。
6、根據示例查詢(Example queries) net.sf.hibernate.expression.Example類許你從指定的執行個體創造查詢條件。
Cat cat = new Cat();
cat.setSex('F');
cat.setColor(Color.BLACK);
List results = session.createCriteria(Cat.class)
.add( Example.create(cat) )
.list();
版本屬性,表示符屬性和關聯都會被忽略。預設情況下,null值的屬性也被排除在外。 You can adjust how the Example is applied. 你可
以調整示例(Example)如何應用。 Example example = Example.create(cat) .excludeZeroes() //exclude zero valued properties
.excludeProperty("color") //exclude the property named "color" .ignoreCase() //perform case insensitive string comparisons
.enableLike(); //use like for string comparisons
List results = session.createCriteria(Cat.class)
.add(example)
.list();
你甚至可以用示例對關聯對象建立criteria。 List results = session.createCriteria(Cat.class) .add(Example.create(cat) )
.createCriteria("mate") .add(Example.create(cat.getMate())) .list();