怎样快速从一个XML文件中查找信息
程序员文章站
2022-03-07 20:03:02
在网络时代,xml文件起到了一个保存和传输数据的作用。soap协议通过xml交流信息,数据库通过xml文件存取等等。那么怎样快速的从一个xml文件中取得所需的信息呢?我们知...
在网络时代,xml文件起到了一个保存和传输数据的作用。soap协议通过xml交流信息,数据库通过xml文件存取等等。那么怎样快速的从一个xml文件中取得所需的信息呢?
我们知道,java的jaxp中和microsoft.net都有xml分析器,microsoft.net是边读边分析,而jaxp是读到内存中然后才进行分析(还有一种是事件机制去读),总而言之,是不利于快速读取。基于此,microsoft.net 和jaxp都提供了xpath机制,来快速定位到xml文件中所需的节点。
例如有一个xml文件:booksort.xml:
<?xml version="1.0"?>
<!-- a fragment of a book store inventory database -->
<bookstore xmlns:bk="urn:samples">
<book genre="novel" publicationdate="1997" bk:isbn="1-861001-57-8">
<title>pride and prejudice</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>24.95</price>
</book>
<book genre="novel" publicationdate="1992" bk:isbn="1-861002-30-1">
<title>the handmaid's tale</title>
<author>
<first-name>margaret</first-name>
<last-name>atwood</last-name>
</author>
<price>29.95</price>
</book>
<book genre="novel" publicationdate="1991" bk:isbn="1-861001-57-6">
<title>emma</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>19.95</price>
</book>
<book genre="novel" publicationdate="1982" bk:isbn="1-861001-45-3">
<title>sense and sensibility</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>19.95</price>
</book>
</bookstore>
如果我们想快速查找”last-name”等于”austen”的所有标题名,可以通过以下方法可以得到:
xmlreadersample.cs
//corelib.net/system.xml.xsl/xpathdocument class
//author :any
using system;
using system.io;
using system.xml;
using system.xml.xpath;
public class xmlreadersample
{
public static void main()
{
xmltextreader myxtreader = new xmltextreader("booksort.xml");
xmlreader myxreader = myxtreader;
xpathdocument doc = new xpathdocument(myxreader);
xpathnavigator nav = doc.createnavigator();
xpathexpression expr;
expr = nav.compile("descendant::book[author/last-name='austen']");
//expr.addsort("title", xmlsortorder.ascending, xmlcaseorder.none, "", xmldatatype.text);
xpathnodeiterator iterator = nav.select(expr);
while (iterator.movenext())
{
xpathnavigator nav2 = iterator.current;
nav2.movetofirstchild();
console.writeline("book title: {0}", nav2.value);
}
}
}
运行这个程序,结果为:
book title: pride and prejudice
book title: emma
book title: sense and sensibility
可以看到查找正确。
利用xpath中的一些功能,也可以实现简单的排序和简单运算。如在数据库中经常要对数据进行汇总,就可用xpath实现。
如:
order.xml
<!--represents a customer order-->
<order>
<book isbn='10-861003-324'>
<title>the handmaid's tale</title>
<price>19.95</price>
</book>
<cd isbn='2-3631-4'>
<title>americana</title>
<price>16.95</price>
</cd>
</order>
和:books.xml
<?xml version="1.0"?>
<!-- this file represents a fragment of a book store inventory database -->
<bookstore>
<book cc="dd" xmlns:bk="urn:sample" xmlns:ns="http://www.any.com" genre="autobiography" publicationdate="1981" isbn="1-861003-11-0">
<title>the autobiography of benjamin franklin</title>
<ns:author>
<first-name>benjamin</first-name>
<last-name>franklin</last-name>
</ns:author>
<price>8.99</price>
</book>
<book genre="novel" publicationdate="1967" isbn="0-201-63361-2">
<title>the confidence man</title>
<author>
<first-name>herman</first-name>
<last-name>melville</last-name>
</author>
<price>11.99</price>
</book>
<book genre="philosophy" publicationdate="1991" isbn="1-861001-57-6">
<title>the gorgias</title>
<author>
<name>plato</name>
</author>
<price>9.99</price>
</book>
</bookstore>
我们可以对该xml文件中的price求和,以得到价格总数。
evaluate.cs
//corelib.net/system.xml.xsl/xpathnavigator class
//author :any
using system;
using system.io;
using system.xml;
using system.xml.xpath;
public class evaluatesample
{
public static void main()
{
evaluatesample myevaluatesample = new evaluatesample();
myevaluatesample.test("books.xml");
}
public void test(string args)
{
try
{
//test evaluate(string);
xpathdocument myxpathdocument = new xpathdocument(args);
xpathnavigator myxpathnavigator = myxpathdocument.createnavigator();
console.writeline(myxpathnavigator.evaluate("sum(descendant::book/price)"));
//testevaluate(xpathexpression);
xmldocument doc = new xmldocument();
doc.load("order.xml");
xpathnavigator nav = doc.createnavigator();
xpathexpression expr = nav.compile("sum(//price/text())");
console.writeline(nav.evaluate(expr));
//testevaluate(xpathexpression);
xpathnodeiterator myxpathnodeiterator = nav.select("descendant::book/title");
expr = nav.compile("sum(//price/text())");
console.writeline(nav.evaluate(expr,myxpathnodeiterator));
}
catch (exception e)
{
console.writeline ("exception: {0}", e.tostring());
}
}
}
运行这个程序,结果如下:
30.97
36.9
36.9
我们可以看到,30.97是books.xml中所有price值的总和,而36.9则是order.xml中所有price值的总和。通过xpah不仅可以快速查找信息,而且还可以对信息进行一些基本的处理。
我们知道,java的jaxp中和microsoft.net都有xml分析器,microsoft.net是边读边分析,而jaxp是读到内存中然后才进行分析(还有一种是事件机制去读),总而言之,是不利于快速读取。基于此,microsoft.net 和jaxp都提供了xpath机制,来快速定位到xml文件中所需的节点。
例如有一个xml文件:booksort.xml:
<?xml version="1.0"?>
<!-- a fragment of a book store inventory database -->
<bookstore xmlns:bk="urn:samples">
<book genre="novel" publicationdate="1997" bk:isbn="1-861001-57-8">
<title>pride and prejudice</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>24.95</price>
</book>
<book genre="novel" publicationdate="1992" bk:isbn="1-861002-30-1">
<title>the handmaid's tale</title>
<author>
<first-name>margaret</first-name>
<last-name>atwood</last-name>
</author>
<price>29.95</price>
</book>
<book genre="novel" publicationdate="1991" bk:isbn="1-861001-57-6">
<title>emma</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>19.95</price>
</book>
<book genre="novel" publicationdate="1982" bk:isbn="1-861001-45-3">
<title>sense and sensibility</title>
<author>
<first-name>jane</first-name>
<last-name>austen</last-name>
</author>
<price>19.95</price>
</book>
</bookstore>
如果我们想快速查找”last-name”等于”austen”的所有标题名,可以通过以下方法可以得到:
xmlreadersample.cs
//corelib.net/system.xml.xsl/xpathdocument class
//author :any
using system;
using system.io;
using system.xml;
using system.xml.xpath;
public class xmlreadersample
{
public static void main()
{
xmltextreader myxtreader = new xmltextreader("booksort.xml");
xmlreader myxreader = myxtreader;
xpathdocument doc = new xpathdocument(myxreader);
xpathnavigator nav = doc.createnavigator();
xpathexpression expr;
expr = nav.compile("descendant::book[author/last-name='austen']");
//expr.addsort("title", xmlsortorder.ascending, xmlcaseorder.none, "", xmldatatype.text);
xpathnodeiterator iterator = nav.select(expr);
while (iterator.movenext())
{
xpathnavigator nav2 = iterator.current;
nav2.movetofirstchild();
console.writeline("book title: {0}", nav2.value);
}
}
}
运行这个程序,结果为:
book title: pride and prejudice
book title: emma
book title: sense and sensibility
可以看到查找正确。
利用xpath中的一些功能,也可以实现简单的排序和简单运算。如在数据库中经常要对数据进行汇总,就可用xpath实现。
如:
order.xml
<!--represents a customer order-->
<order>
<book isbn='10-861003-324'>
<title>the handmaid's tale</title>
<price>19.95</price>
</book>
<cd isbn='2-3631-4'>
<title>americana</title>
<price>16.95</price>
</cd>
</order>
和:books.xml
<?xml version="1.0"?>
<!-- this file represents a fragment of a book store inventory database -->
<bookstore>
<book cc="dd" xmlns:bk="urn:sample" xmlns:ns="http://www.any.com" genre="autobiography" publicationdate="1981" isbn="1-861003-11-0">
<title>the autobiography of benjamin franklin</title>
<ns:author>
<first-name>benjamin</first-name>
<last-name>franklin</last-name>
</ns:author>
<price>8.99</price>
</book>
<book genre="novel" publicationdate="1967" isbn="0-201-63361-2">
<title>the confidence man</title>
<author>
<first-name>herman</first-name>
<last-name>melville</last-name>
</author>
<price>11.99</price>
</book>
<book genre="philosophy" publicationdate="1991" isbn="1-861001-57-6">
<title>the gorgias</title>
<author>
<name>plato</name>
</author>
<price>9.99</price>
</book>
</bookstore>
我们可以对该xml文件中的price求和,以得到价格总数。
evaluate.cs
//corelib.net/system.xml.xsl/xpathnavigator class
//author :any
using system;
using system.io;
using system.xml;
using system.xml.xpath;
public class evaluatesample
{
public static void main()
{
evaluatesample myevaluatesample = new evaluatesample();
myevaluatesample.test("books.xml");
}
public void test(string args)
{
try
{
//test evaluate(string);
xpathdocument myxpathdocument = new xpathdocument(args);
xpathnavigator myxpathnavigator = myxpathdocument.createnavigator();
console.writeline(myxpathnavigator.evaluate("sum(descendant::book/price)"));
//testevaluate(xpathexpression);
xmldocument doc = new xmldocument();
doc.load("order.xml");
xpathnavigator nav = doc.createnavigator();
xpathexpression expr = nav.compile("sum(//price/text())");
console.writeline(nav.evaluate(expr));
//testevaluate(xpathexpression);
xpathnodeiterator myxpathnodeiterator = nav.select("descendant::book/title");
expr = nav.compile("sum(//price/text())");
console.writeline(nav.evaluate(expr,myxpathnodeiterator));
}
catch (exception e)
{
console.writeline ("exception: {0}", e.tostring());
}
}
}
运行这个程序,结果如下:
30.97
36.9
36.9
我们可以看到,30.97是books.xml中所有price值的总和,而36.9则是order.xml中所有price值的总和。通过xpah不仅可以快速查找信息,而且还可以对信息进行一些基本的处理。