title: JDOM parses much slower than DOM
body: <p>I have 2 methods to parse the same XML document using <code>DOM</code> and <code>JDOM</code>. I expected <code>JDOM</code> runs faster and consumes less memory than <code>DOM</code> but actually <code>JDOM</code> run several times slower and consumed much much more memory in my benchmark. I'm using JMH as the benchmarking framework.</p>
  
  <pre><code>import org.openjdk.jmh.annotations.*;
  import org.openjdk.jmh.annotations.BenchmarkMode;
  import org.openjdk.jmh.annotations.Mode;
  import org.openjdk.jmh.annotations.OutputTimeUnit;
  import org.openjdk.jmh.runner.Runner;
  import org.openjdk.jmh.runner.RunnerException;
  import org.openjdk.jmh.runner.options.Options;
  import org.openjdk.jmh.runner.options.OptionsBuilder;
  import java.io.File;
  import java.util.concurrent.TimeUnit;
  import java.io.IOException;
  import java.util.List;
  
  import javax.xml.parsers.DocumentBuilderFactory;
  import javax.xml.parsers.DocumentBuilder;
  import org.w3c.dom.Document;
  
  import org.jdom2.Document;
  import org.jdom2.Element;
  import org.jdom2.JDOMException;
  import org.jdom2.input.SAXBuilder;
  
  @BenchmarkMode(Mode.SingleShotTime) 
  @OutputTimeUnit(TimeUnit.MILLISECONDS)
  @Warmup(iterations = 10, time = 1, timeUnit = TimeUnit.MILLISECONDS)
  @Measurement(iterations = 1, time = 200, timeUnit = TimeUnit.MILLISECONDS)
  @State(Scope.Benchmark)
  public class MyBenchmark {
  
      @Param({"1.xml"})
      public String xml;
  
      @Benchmark 
      public void DOM(){
  
          try {
              File fXmlFile = new File(xml);
              DocumentBuilderFactory dbFactory = 
              DocumentBuilderFactory.newInstance();
              DocumentBuilder dBuilder = dbFactory.newDocumentBuilder();
              Document doc = dBuilder.parse(fXmlFile);
          } catch (Exception e) {
              e.printStackTrace();
          }
  
      @Benchmark 
      public void JDOM(){
          SAXBuilder builder = new SAXBuilder();
          File xmlFile = new File(xml);
  
          try {
              Document document = (Document) builder.build(xmlFile);
          } catch (IOException io) {
              System.out.println(io.getMessage());
          } catch (JDOMException jdomex) {
              System.out.println(jdomex.getMessage());
          }
      }
  }
  </code></pre>
  
  <p>DOM results</p>
  
  <pre><code>Benchmark                                         (xml)  Mode  Cnt         Score          Error   Units
  MyBenchmark.DOM                                   1.xml    ss   10       126.823 ±       16.821   ms/op
  MyBenchmark.DOM:·gc.alloc.rate                    1.xml    ss   10        92.618 ±        2.481  MB/sec
  MyBenchmark.DOM:·gc.alloc.rate.norm               1.xml    ss   10  60869076.800 ±      130.041    B/op
  </code></pre>
  
  <p>JDOM2 results</p>
  
  <pre><code>Benchmark                                          (xml)  Mode  Cnt           Score           Error   Units
  MyBenchmark.JDOM                                   1.xml    ss   10         789.941 ±        81.293   ms/op
  MyBenchmark.JDOM:·gc.alloc.rate                    1.xml    ss   10        2248.753 ±       141.240  MB/sec
  MyBenchmark.JDOM:·gc.alloc.rate.norm               1.xml    ss   10  3037712408.000 ±         0.001    B/op
  </code></pre>
  
  <p>The document has 12MB in size and contains 192,000 elements. Below is the structure of the XML document, the document has 38,400 level 1 elements:</p>
  
  <pre><code>&lt;?xml version="1.0" encoding="UTF-8"?&gt;
  &lt;Root&gt;
     &lt;level_1 Element_Number="1"&gt;
        &lt;level_2 Attribute_Level_2="Attribute_Level_2"&gt;
           &lt;level_3_1 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_1&gt;
           &lt;level_3_2 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_2&gt;
           &lt;level_3_3 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_3&gt;
        &lt;/level_2&gt;
     &lt;/level_1&gt;
     &lt;level_1 Element_Number="2"&gt;
        &lt;level_2 Attribute_Level_2="Attribute_Level_2"&gt;
           &lt;level_3_1 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_1&gt;
           &lt;level_3_2 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_2&gt;
           &lt;level_3_3 Attribute_Level_3="Attribute_Level_3"&gt;test&lt;/level_3_3&gt;
        &lt;/level_2&gt;
     &lt;/level_1&gt;
  </code></pre>
  
  <p>Can anyone explain this? I'm using JDOM 2.0.2 anyway.</p>
  
  <p><strong>Edit:</strong> DOM vs JDOM benchmarks for small documents (5000 to 25,000 elements)
  <a href="https://i.stack.imgur.com/FjZaz.png" rel="nofollow noreferrer"><img src="https://i.stack.imgur.com/FjZaz.png" alt="enter image description here"></a></p>