L
Larry Coon
I'm trying to figure out the right way to use the xpath api
under 1.5. I'm not sure I'm doing it the right way when a
node has multiple children -- I can get to the data, but my
technique seems kludgy. The samples I found online tell you
how to get a NodeList, but don't really help you from there.
First, here is a sample document (XPathTest.xml):
<?xml version="1.0" encoding="utf-8"?>
<test>
<one>This is a single item</one>
<many>
<item>This is one of many items #1</item>
<item>This is one of many items #2</item>
<item>This is one of many items #3</item>
</many>
</test>
-----
Here's an SSCCE. The technique I use to get the single item
is easy enough, but I start to scratch my head when I go after
the many items:
import java.io.*;
import javax.xml.parsers.*;
import javax.xml.xpath.*;
import org.w3c.dom.*;
public class TestXPath {
public TestXPath(String configFileName) {
try {
DocumentBuilderFactory domFactory =
DocumentBuilderFactory.newInstance();
DocumentBuilder builder = domFactory.newDocumentBuilder();
Document document = builder.parse(new File(configFileName));
XPathFactory xFactory = XPathFactory.newInstance();
XPath xPath = xFactory.newXPath();
String s1 = xPath.evaluate("/test/one", document);
System.out.println("One item: " + s1);
NodeList nodes = (NodeList)
xPath.evaluate("/test/many/item",
document, XPathConstants.NODESET);
int length = nodes.getLength();
System.out.println("Number of items: " + length);
for (int i = 0; i < length; i++) {
String s2 = xPath.evaluate("/test/many/item["
+ (i + 1) + "]", document);
System.out.println("Many items #" + i + ": " + s2);
}
}
catch (Exception x) { x.printStackTrace(); }
}
public static void main(String[] args) {
new TestXPath("XPathTest.xml");
}
}
-----
I realize that a NodeList isn't Iterable, so I need to use a for loop
to get the individual items. But the only thing I'm using the NodeList
for is to get a count -- I go back to the DOM to retrieve the actual
data. This doesn't seem right. Should I be using XPath on the NodeList
to get at the data more directly? I tried various ways, and didn't get
anything to work. Any advice?
under 1.5. I'm not sure I'm doing it the right way when a
node has multiple children -- I can get to the data, but my
technique seems kludgy. The samples I found online tell you
how to get a NodeList, but don't really help you from there.
First, here is a sample document (XPathTest.xml):
<?xml version="1.0" encoding="utf-8"?>
<test>
<one>This is a single item</one>
<many>
<item>This is one of many items #1</item>
<item>This is one of many items #2</item>
<item>This is one of many items #3</item>
</many>
</test>
-----
Here's an SSCCE. The technique I use to get the single item
is easy enough, but I start to scratch my head when I go after
the many items:
import java.io.*;
import javax.xml.parsers.*;
import javax.xml.xpath.*;
import org.w3c.dom.*;
public class TestXPath {
public TestXPath(String configFileName) {
try {
DocumentBuilderFactory domFactory =
DocumentBuilderFactory.newInstance();
DocumentBuilder builder = domFactory.newDocumentBuilder();
Document document = builder.parse(new File(configFileName));
XPathFactory xFactory = XPathFactory.newInstance();
XPath xPath = xFactory.newXPath();
String s1 = xPath.evaluate("/test/one", document);
System.out.println("One item: " + s1);
NodeList nodes = (NodeList)
xPath.evaluate("/test/many/item",
document, XPathConstants.NODESET);
int length = nodes.getLength();
System.out.println("Number of items: " + length);
for (int i = 0; i < length; i++) {
String s2 = xPath.evaluate("/test/many/item["
+ (i + 1) + "]", document);
System.out.println("Many items #" + i + ": " + s2);
}
}
catch (Exception x) { x.printStackTrace(); }
}
public static void main(String[] args) {
new TestXPath("XPathTest.xml");
}
}
-----
I realize that a NodeList isn't Iterable, so I need to use a for loop
to get the individual items. But the only thing I'm using the NodeList
for is to get a count -- I go back to the DOM to retrieve the actual
data. This doesn't seem right. Should I be using XPath on the NodeList
to get at the data more directly? I tried various ways, and didn't get
anything to work. Any advice?