在PHP中处理大型XML的最佳方法

时间:2009-07-22 17:56:06

标签: php xml parsing simplexml large-files

我必须解析php中的大型XML文件,其中一个是6.5 MB,它们可能更大。 正如我所读到的SimpleXML扩展,将整个文件加载到一个对象中,这可能效率不高。 根据您的经验,最好的方法是什么?

7 个答案:

答案 0 :(得分:22)

对于大文件,您需要使用SAX parser而不是DOM解析器。

使用DOM解析器,它将读入整个文件并将其加载到内存中的对象树中。使用SAX解析器,它将按顺序读取文件并调用用户定义的回调函数来处理数据(开始标记,结束标记,CDATA等)。

使用SAX解析器,您需要自己维护状态(例如,您当前使用的是哪个标记),这使得它更复杂,但对于大文件,它将更加高效地记忆。

答案 1 :(得分:11)

我接受它:

https://github.com/prewk/XmlStreamer

一个简单的类,它将在传输文件时将所有子元素提取到XML根元素。 测试来自pubmed.com的108 MB XML文件。

class SimpleXmlStreamer extends XmlStreamer {
    public function processNode($xmlString, $elementName, $nodeIndex) {
        $xml = simplexml_load_string($xmlString);

        // Do something with your SimpleXML object

        return true;
    }
}

$streamer = new SimpleXmlStreamer("myLargeXmlFile.xml");
$streamer->parse();

答案 2 :(得分:7)

对大型XML文件使用DOMDocument时,请不要忘记在LIBXML_PARSEHUGE方法的选项中传递load()标记。 (同样适用于DOMDocument对象的其他load方法)

    $checkDom = new \DOMDocument('1.0', 'UTF-8');
    $checkDom->load($filePath, LIBXML_PARSEHUGE);

(使用120mo XML文件)

答案 3 :(得分:6)

正如Eric Petroelje建议的那样,SAX Parser对于大型XML文件会更好。 DOM解析器加载整个XML文件并允许您运行xpath查询 - 一个SAX(XML的简单API)解析器将一次读取一行并为您提供钩点以进行处理。

答案 4 :(得分:3)

这真的取决于你想要对数据做什么?你是否需要在记忆中有效地使用它?

就今天的计算机而言,6.5 MB并不是那么大。例如,您可以ini_set('memory_limit', '128M');

但是,如果您的数据可以流式传输,则可能需要查看SAX parser。这实际上取决于您的使用需求。

答案 5 :(得分:1)

SAX解析器是要走的路。我发现如果你没有保持井井有条,SAX解析就会变得混乱。

我使用基于STX(Streaming Transformations for XML)的方法来解析大型XML文件。我使用SAX方法构建一个SimpleXML对象来跟踪当前上下文中的数据(即只是根节点和当前节点之间的节点)。然后使用其他函数来处理SimpleXML文档。

答案 6 :(得分:1)

我需要解析碰巧在每一行上都有一个元素的大型XML文件(StackOverflow数据转储)。在这种特定情况下,一次读取一行文件并使用SimpleXML解析每一行就足够了。对我来说,这样做的好处就是不必学习任何新东西。