Car*_*ton 5 php xml xmlreader out-of-memory xml-parsing
我有一个大的XML文件(大约400MB),我需要确保在开始处理之前格式良好.
我尝试过的第一件事就是类似于下面的内容,这很棒,因为我可以发现XML是否格式不正确以及XML的哪些部分"糟糕"
$doc = simplexml_load_string($xmlstr);
if (!$doc) {
$errors = libxml_get_errors();
foreach ($errors as $error) {
echo display_xml_error($error);
}
libxml_clear_errors();
}
Run Code Online (Sandbox Code Playgroud)
还试过......
$doc->load( $tempFileName, LIBXML_DTDLOAD|LIBXML_DTDVALID )
Run Code Online (Sandbox Code Playgroud)
我用一个大约60MB的文件测试了这个,但是任何更大的东西(~400MB)都会导致一些对我来说是"新鲜杀手"的东西,在看起来像是30秒之后终止脚本.
我以为我可能需要增加脚本的内存,以便在处理60MB时找出峰值使用量,并相应地调整大小,并且还会关闭脚本时间限制以防万一.
set_time_limit(0);
ini_set('memory_limit', '512M');
Run Code Online (Sandbox Code Playgroud)
不幸的是,这不起作用,因为如果内存负载(即使是正确的术语?)一直很高,那么oom杀手似乎是一个linux的东西.
如果我能以某种方式加载xml,这将是很好的,因为我想这将减少内存负载,以便oom杀手不会坚持它的肥胖鼻子并杀死我的过程.
有没有人有任何验证大型XML文件和捕获错误形成错误的经验,我读过很多帖子都指向可能解决我问题的SAX和XMLReader.
更新 所以@chiborg几乎为我解决了这个问题...这个方法唯一的缺点就是我没有看到文件中的所有错误,只是第一个失败,我认为这是有意义的,因为我认为它无法解析失败的第一个点.
当使用simplexml时...它能够捕获文件中的大部分问题并在最后向我展示这很好.
由于SimpleXML和DOM API将始终将文档加载到内存中,因此使用SAX或XMLReader等流式解析器是更好的方法.
通过示例页面中的代码,它可能如下所示:
$xml_parser = xml_parser_create();
if (!($fp = fopen($file, "r"))) {
die("could not open XML input");
}
while ($data = fread($fp, 4096)) {
if (!xml_parse($xml_parser, $data, feof($fp))) {
$errors[] = array(
xml_error_string(xml_get_error_code($xml_parser)),
xml_get_current_line_number($xml_parser));
}
}
xml_parser_free($xml_parser);
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1454 次 |
| 最近记录: |