پرس و جوی محتوای XML با XPath
XPath پیشنهاد رسمی W3C برای پرس و جو و جست و جو در محتوای XML است، در حقیقت XPath استانداری است که زبانی را در اختیار ما قرار میدهد که با استفاده از آن میتوانیم المانها و صفتها مختلف یک فایلXML را مورد بررسی قرار دهیم.
XPath دارای ویژگیها و امکانات زیر است:
Path Expression
Path Expression عبارت متنی است که به ما اجازه میدهد گره یا گرههایی را از داخل یک محتوای XML استخراج کنیم، جدول زیر عبارات مهم و کاربردی Path Expression را نشان میدهد.
عبارت | عملکرد | |
node-name | به کار بردن نام گره باعث میشود تا تمام گرههای با نام مورد نظر انتخاب شوند. | |
/ | مشخص میکند که انتخاب و جست و جو از ابتدای فایل صورت گیرد. | |
// | تمام گرهها صرف نظر از مکان آنها انتخاب میشوند. | |
. | گره فعلی را انتخاب میکند. | |
.. | پدر گره فعلی را انتخاب میکند. | |
@ | برای انتخاب بر حسب صفت به کار میرود. |
Predicates
پس از ساخت یک لیست توسط Path Expression با استفاده از Predicate میتوانیم گره یا گرههای خاصی را انتخاب میکنیم، Predicate با عبارت […] مشخص میشود که به جای … میتوانیم از توابع استاندارد، اندیس یا عبارات پیچیده تر برای انتخاب گرههای خاص استفاده کنیم، در ادامه با مثال با این موضوع آشنا میشویم:
عبارت | عملکرد | |
/class/student[1] | اولین گره student که زیر گره class باشد را انتخاب میکند. | |
/class/student[3] | سومین گره student که زیر گره class باشد را انتخاب میکند. | |
/class/student[last()] | آخرین گره student که زیر گره class باشد را انتخاب میکند. | |
/class/student[last()-1] | گره ماقبل آخر را با شرایط قبلی انتخاب میکند. | |
//student[@sid=’333’] | تمام گرههای student که دارای sid برابر با 333 هستند را انتخاب میکند. | |
/class/student[position()<3] | تمام گرههای student زیر گره class که اندیس آنها از 3 کمتر است را انتخاب میکند (یعنی دو گره ابتدایی انتخاب میشوند.)در اینجا اندیس از یک شروع میشود. |
استفاده از XPath در جاوا:
خوشبختانه در جاوا با استفاده از کتابخانههای توکار میتوانیم به سادگی از امکاناتXPath استفاده کنیم، به صورت کلی استفاده از XPath شامل مراحل زیر است:
- کتابخانههای مورد نیاز را import کنیم که معمولاً موارد زیر کافی هستند:
- برای خواندن از فایل یک DocumentBuilder ایجاد کنیم:
- یک Document ایجاد کنیم و محتوای XML را از یک فایل یا استریم بخوانیم
- یک شیء از کلاس XPath ایجاد کنیم:
- Path Expression مورد نظر را ساخته و آن را با متد compile کامپایل کنیم.
- با استفاده از متد evaluate نتیجه مورد نظر را محاسبه کنیم .
import org.w3c.dom.*; import org.xml.sax.*; import javax.xml.parsers.*; import javax.xml.xpath.*; import java.io.*;
DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); DocumentBuilder builder = factory.newDocumentBuilder();
Document doc = builder.parse(input);
XPath xPath = XPathFactory.newInstance().newXPath();
XPathExpression expr = xPath.compile(XPATH_EXPRESSION_STRING);
NodeList nodeList = (NodeList) expr.evaluate(doc, XPathConstants.NODESET);
در ادامه با استفاده از چند مثال به صورت عملی با موارد فوق آشنا میشویم. قبل از ادامه یک فایل XML به نام sample.xml ایجاد میکنیم و محتوای زیر را در آن مینویسیم و در درایو D ذخیره میکنیم:
<?xml version="1.0" encoding="utf-8" ?> <Persons> <Person name="John Smith"> <Age>30</Age> <Gender>Male</Gender> </Person> <Person name="Mike Folley"> <Age>25</Age> <Gender>Male</Gender> </Person> <Person name="Lisa Carter"> <Age>22</Age> <Gender>Female</Gender> </Person> <Person name="Jerry Frost"> <Age>27</Age> <Gender>Male</Gender> </Person> <Person name="Adam Wong"> <Age>35</Age> <Gender>Male</Gender> </Person> </Persons>
برای انتخاب گره ای از فایل بالا که خاصیت Name آن برابری John Smith است به صورت زیر عمل می کنیم :
1: import org.w3c.dom.*; 2: import javax.xml.parsers.*; 3: import javax.xml.xpath.*; 4: import java.io.*; 5: 6: public class XPathDemo 7: { 8: static void printNode(Node n) 9: { 10: System.out.println("------"); 11: Element e = (Element)n; 12: 13: //Parent Node 14: System.out.println(n.getNodeName() + " Name: " + e.getAttribute(" Name")); 15: 16: //Age 17: String Age = e.getElementsByTagName("Age").item(0).getTextContent(); 18: System.out.println("Person Age: " + Age); 19: 20: //Gender 21: String Gender = e.getElementsByTagName("Gender").item(0).getTextContent(); 22: System.out.println("Person Gender: " + Gender); 23: } 24: 25: public static void main(String[] args) throws Exception 26: { 27: 28: String XPATH_EXPRESSION_STRING = "//Person[@name='John Smith']"; 29: 30: File myXMLFile = new File("D:/sample.xml"); 31: 32: DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance(); 33: DocumentBuilder dBuilder = dbFactory.newDocumentBuilder(); 34: 35: Document doc = dBuilder.parse(myXMLFile); 36: 37: XPath xPath = XPathFactory.newInstance().newXPath(); 38: XPathExpression expr = xPath.compile(XPATH_EXPRESSION_STRING); 39: 40: NodeList list = (NodeList)expr.evaluate(doc, XPathConstants.NODESET); 41: 42: int listSize = list.getLength(); 43: System.out.println(listSize); 44: for (int i = 0; i < listSize; i++) 45: { 46: Node nodeI = list.item(i); 47: printNode(nodeI); 48: } 49: } 50: }
1 ------ Person Name: John Smith Person Age: 30 Person Gender: Male
برای انتخاب گرههای از نوع Person که جنسیت (Gender) در آنها زن (Female) باشد، کافی است که خط 28 کد بالا را به صورت زیر تغییر دهیم:
String XPATH_EXPRESSION_STRING ="//Person[Gender='Female']";
1 ------ Person Name: Lisa Carter Person Age: 22 Person Gender: Female
برای انتخاب گرههای از نوع Person که سن (Age) آنها بیشتر از 25 سال باشد، کافی است که خط 28 کد بالا را به صورت زیر تغییر دهیم:
String XPATH_EXPRESSION_STRING ="//Person[Age > 25]";
3 ------ Person Name: John Smith Person Age: 30 Person Gender: Male ------ Person Name: Jerry Frost Person Age: 27 Person Gender: Male ------ Person Name: Adam Wong Person Age: 35 Person Gender: Male