在JAVA對象中,如何進行有效查詢呢,這一直是個很值得探討的問題.大家知道,在XML中,要找元素如何找呢?沒錯,通過XPATH
是個不錯的辦法,同樣道理,新近發現原來在JAVA中,也居然有象XPATH裡的東西,這就是著名的apache commons庫中包含的jxpath包中所提供的功能,這可以在http://jakarta.apache.org/commons/jxpath/中找到相關下載.下面來簡單介紹一下(注:本文內容主要來自
http://today.java.net/pub/a/today/2006/08/03/java-object-querying-using-jxpath.html
,本人有所改動和潤色)
什麼是JXPATH
首先,JXPATH是通過簡單的運算式,可以在JAVA的類對象層次中進行查詢.我們還是來看簡單的例子來說明問題:
比如,我們的例子中,有一些公司,每間公司有不同的部門,每個不同的僱員,而且當然,公司有它們的CEO.僱員還有比如姓名,電話等屬性.
假設我們要尋找在California的公司中,有哪些公司的部門中有超過10位員工的話,以前會這樣寫的
for (Iterator companies = database.getCompanies().iterator(); companies.hasNext();)
{
//獲得所有公司
Company company = (Company)companies.next();
//獲得在California的公司
if (company.getLocation().equals("CAA")) {
for (Iterator departments =company.getDepartments().iterator();departments.hasNext(); )
{
//獲得公司的所有部門
Department department =
(Department)departments.next();
if (department.getEmployees().size() > 10) {
System.out.println(department);
}
}
}
}
而如果用JXPATH的話,可以這樣寫
Iterator departments = context.iterate(
"/companies[location='CA']" +
"/departments[count(employees) > 10]");
while (departments.hasNext()) {
System.out.println(departments.next());
}
可以看到,用了JXPATH的話,只需要簡單指定好運算式,馬上就可以了.下面來簡單介紹下一些寫法
比如:
要多的所有的公司:/companies
獲得公司下的部門:/companies/departments
獲得在某個地方的公司:/companies[location='CA'],這裡,location為companies的屬性
要獲得位於CA的公司中含有開發部門的公司的話,可以這樣:
/companies[location='CA']/departments[contains(name, 'Development')]
要獲得某個部門僱員數大於10人的:/companies/departments[count(employees) > 10]
要獲得SUN公司下第二個部門:/companies[name='Sun Microsystems']/departments[2]
要注意的是,JXPATH的序號是從1開始,不是從0開始
和XPATH類似,可以象這樣
/companies[name='Sun Microsystems']/
departments[last()]
接下來說下如何配合JAVA代碼來實現查詢
首先,對比如對於company,employee,department這三個類,都必須設定getter,setter方法,
然後,比如要有
public List getCompanies();
後,則可以使用
/Companies來查詢了
而每個公司下面要查詢所有的部門的話,先設定
public List getDepartments();
方法,
然後再用/companies/departments可以查詢了;
提供public String getName();方法,則在下面的情境中會被調用:
/companies/departments[name='Server Development']
又比如,假設已經設定了一個MAP,裡面存放某人的電話,比如有公司電話,私人電話:
Map numbers = employee.getTelephoneNumbers();
String workNumber =
(String)numbers.get("work number");
上面是取得某個僱員的公司電話,但必須這樣寫JXPATH
.../employees[1]/
telephoneNumbers[@name='work number']
@name是用來指定MAP中的KEY的,而不能簡單將上面的寫成
.../employees[1]/
telephoneNumbers/work number
最後,我們可以結合起來使用jxpath了,首先先聲明根對象,也就是說,你要先構造出一個類層次出來,比如已經構造出一個類層次,叫
database類,則:
JXPathContext context = JXPathContext.
newContext(database);
其中database類裡面已經有所有的公司的執行個體了,這裡先取出其上下文context;然後,
Iterator departments = context.iterate("/companies[location='WA']" +
"/departments[count(employees) > 10]");
則取出所有在WA的那些部門人數>10的所有公司的集合了
最後輸出:
while (departments.hasNext()) {
Department dept = (Department)i.next();
}
看,多簡單呀.
最後,強烈大家去下載本文的例子去看看,在ECLIPSE裡跑一下就可以了,寫的很清晰
代碼:http://today.java.net/today/2006/08/03/source_code.tar.gz