Hastighed på XPath
Hej, jeg sidder og roder med at optimere gammel kode, nærmere bestemt gammel "manuel" iteration af XML med XPath, men det viser sig, at den gamle kode er markant hurtigere. Hvad er grunden til det?Her ses et lille men komplet eksempel:
public class XPathFun {
/* Eksempel på xml
<Language>
<Group name="General">
<String name="Ok">Ok</String>
<String name="Cancel">Annuller</String>
</Group>
<Group name="Login">
<String name="Username">Brugernavn</String>
<String name="Password">Adgangskode</String>
</Group>
</Language>
*/
public static void main(String[] args) throws Exception {
System.out.println(getStringByDOM("General", "Cancel"));
System.out.println(getStringByXPath("General", "Cancel"));
}
private static String getStringByXPath(String group, String key) throws Exception{
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
DocumentBuilder db = dbf.newDocumentBuilder();
Document doc = db.parse("C:\\Temp\\Dansk.xml");
String xpathSelector = "//Language/Group[@name='" + group + "']/String[@name='" + key + "']/text()";
XPath xpath = XPathFactory.newInstance().newXPath();
try {
Node node = (Node)xpath.evaluate(xpathSelector, doc.getDocumentElement(), XPathConstants.NODE);
if(node != null) {
return node.getNodeValue();
}
}
catch(XPathExpressionException e) {
e.printStackTrace();
}
return key;
}
private static String getStringByDOM(String group, String key) throws Exception {
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
DocumentBuilder db = dbf.newDocumentBuilder();
Document doc = db.parse("C:\\Temp\\Dansk.xml");
NodeList elements = doc.getElementsByTagName("Group");
for(int i=0; i < elements.getLength(); i++){
String groupCandidate = elements.item(i).getAttributes().item(0).getTextContent();
if(groupCandidate.equals(group)){
NodeList children = ((Element)elements.item(i)).getElementsByTagName("String");
for(int c=0; c < children.getLength(); c++){
String stringCandidate = children.item(c).getAttributes().item(0).getTextContent();
if(stringCandidate.equals(key)){
return children.item(c).getTextContent();
}
}
}
}
return key;
}
}