マイペースなプログラミング日記

DTMやプログラミングにお熱なd-kamiがマイペースに書くブログ

XPathをコンパイルしておくと、どの程度速くなるのか気になったので実験してみた

XPath#evaluateを直接呼び出すのと、XPath#compileしておいたXPathExpression#evaluateではコンパイルしているぶんXPathExpression#evaluateの方が速いんだろうなぁ、とは考えていたがどの程度差があるのか気になって実験してみた。


利用したXMLhttp://d.hatena.ne.jp/d-kami/rss2をローカルに保存してrss2というファイル名にしておき、XPathの"/rss/channel/title/text()"を1万回評価した時間を計測した

XPath#evaluateを直接呼び出したプログラム

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilder;
import org.w3c.dom.Document;

import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathFactory;
import javax.xml.xpath.XPathExpression;

import java.io.IOException;
import org.xml.sax.SAXException;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPathExpressionException;

public class XPathTest {
    public static void main(String[] args) 
        throws ParserConfigurationException, SAXException, 
               IOException, XPathExpressionException {

        DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
        dbFactory.setNamespaceAware(true);

        DocumentBuilder builder = dbFactory.newDocumentBuilder();
        Document document = builder.parse("rss2");

        XPathFactory factory = XPathFactory.newInstance();
        XPath xpath = factory.newXPath();

        long start, end;

        start = System.currentTimeMillis();

        for(int i = 0; i < 10000; i++){
            xpath.evaluate("/rss/channel/title/text()", document);
        }

        end = System.currentTimeMillis();

        double time = (double)(end - start) / 1000;
        System.out.println(time + "秒かかりました");
    }
}




XPath#compileしてからXPathExpression#evaluateを呼び出したプログラム

import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.DocumentBuilder;
import org.w3c.dom.Document;

import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathFactory;
import javax.xml.xpath.XPathExpression;

import java.io.IOException;
import org.xml.sax.SAXException;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.xpath.XPathExpressionException;

public class XPathTest {
    public static void main(String[] args) 
        throws ParserConfigurationException, SAXException, 
               IOException, XPathExpressionException {

        DocumentBuilderFactory dbFactory = DocumentBuilderFactory.newInstance();
        dbFactory.setNamespaceAware(true);

        DocumentBuilder builder = dbFactory.newDocumentBuilder();
        Document document = builder.parse("rss2");

        XPathFactory factory = XPathFactory.newInstance();
        XPath xpath = factory.newXPath();
        XPathExpression expr = xpath.compile("/rss/channel/title/text()");

        long start, end;

        start = System.currentTimeMillis();

        for(int i = 0; i < 10000; i++){
            expr.evaluate(document);
        }

        end = System.currentTimeMillis();

        double time = (double)(end - start) / 1000;
        System.out.println(time + "秒かかりました");
    }
}

何度か繰り返して得た結果は
XPath#evaluateを直接呼び出したプログラム
6.7〜6.8秒

XPath#compileしてからXPathExpression#evaluateを呼び出したプログラム
6.8〜6.9秒


と1万回繰り返して0.1秒以下の差とほとんど差が無かった。もっと差が出ると思ったけど特に差がでなかったのは意外だった。やり方次第で差がでるのだろうか?