繁体   English   中英

DOM与SAX XML解析大文件

[英]DOM vs SAX XML parsing for large files

背景:

我有一个大的OWL(Web Ontology Language)文件(大约125MB或150万行),我想解析为一组制表符分隔值。 我一直在研究SAX和DOM XML解析器,并发现了以下内容:

  • SAX允许逐个节点地读取文档,因此整个文档不在内存中。
  • DOM允许将整个文档同时放在内存中,但是有一个荒谬的开销。

SAX vs DOM用于大文件:

据我了解,

  • 如果我使用SAX ,我将不得不逐个节点地迭代150万行代码。
  • 如果我使用DOM ,我会有很大的开销,但结果会很快返回。

问题:

我需要能够在相同长度的类似文件上多次使用此解析器。

因此,我应该使用哪个解析器?

加分点:有没有人知道JavaScript的任何好的解析器。 我意识到很多都是为Java而制作的,但我对JavaScript更加满意。

遇见StAX

就像SAX一样, StAX遵循Streaming编程模型来解析XML。 但是,它是DOM的双向读/写支持,易用性和SAX的CPU和内存效率之间的交叉。

SAX是只读的,并且推送解析强制您在那里处理事件和错误,然后在解析输入时。 另一方面, StAX是一个拉解析器 ,它允许客户端在需要时调用解析器上的方法。 这也意味着应用程序可以同时读取多个XML文件。

JAXP API比较

╔══════════════════════════════════════╦═════════════════════════╦═════════════════════════╦═══════════════════════╦═══════════════════════════╗
║          JAXP API Property           ║          StAX           ║           SAX           ║          DOM          ║           TrAX            ║
╠══════════════════════════════════════╬═════════════════════════╬═════════════════════════╬═══════════════════════╬═══════════════════════════╣
║ API Style                            ║ Pull events; streaming  ║ Push events; streaming  ║ In memory tree based  ║ XSLT Rule based templates ║
║ Ease of Use                          ║ High                    ║ Medium                  ║ High                  ║ Medium                    ║
║ XPath Capability                     ║ No                      ║ No                      ║ Yes                   ║ Yes                       ║
║ CPU and Memory Utilization           ║ Good                    ║ Good                    ║ Depends               ║ Depends                   ║
║ Forward Only                         ║ Yes                     ║ Yes                     ║ No                    ║ No                        ║
║ Reading                              ║ Yes                     ║ Yes                     ║ Yes                   ║ Yes                       ║
║ Writing                              ║ Yes                     ║ No                      ║ Yes                   ║ Yes                       ║
║ Create, Read, Update, Delete (CRUD)  ║ No                      ║ No                      ║ Yes                   ║ No                        ║
╚══════════════════════════════════════╩═════════════════════════╩═════════════════════════╩═══════════════════════╩═══════════════════════════╝

参考:
StAX属于您的XML工具箱吗?

StAX是一种“拉”型API。 如上所述,有Cursor和Event Iterator API。 API有读写两面。 它比SAX更适合开发人员。 与SAX一样,StAX不需要将整个文档保存在内存中。 但是,与SAX不同,不需要读取整个文档。 部分可以跳过。 这可能导致甚至比SAX提高性能。

你最想要SAX。

DOM不一定更快; 它可能会慢一点,如果它可以工作,并且,正如你所说,你需要在记忆中保持很多,可能是不必要的。

OWL XML语法相当平坦,但包含许多交叉引用。

如果您需要解决交叉引用,那么流式方法(如SAX或StAX)是不可行的; 您需要在内存中构建一个包含整个树的数据结构。 如果你打算使用内存中的树,不要使用DOM,使用一个更现代的模型,如JDOM2或XOM - 它们更有效,更实用。

如果流式方法是可行的 - 也就是说,如果输入和输出之间存在非常直接的对应关系,那么StAX比SAX更容易使用,因为您可以将当前状态保存在Java堆栈中的变量中,而不是需要复杂的数据结构以维持调用之间的状态。

但是,还有另一种选择; 你可以在流式XSLT 3.0中编写全部内容。 说实话,这是前沿,你的学习时间可能会更大; 而且它不是开源的; 但你最终可能会得到10行代码而不是300行代码的解决方案。

我还没有尝试过其他流媒体技术,比如XStream。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM