解析50GB xml文件,得到关于内存不足的致命错误


parsing 50GB xml file, getting fatal error regarding out of memory

我正在解析一个大小接近50GB的xml文件,使用下面的代码。得到致命错误:内存不足(已分配524288)(试图分配5000000001字节)

    $xml_parser = xml_parser_create();
    xml_parser_set_option($xml_parser, XML_OPTION_CASE_FOLDING, false);
    xml_set_element_handler($xml_parser, "startElement", "endElement");
    xml_set_character_data_handler($xml_parser, "characterData");
    if (!($fp = fopen($file, "r"))) {
        die("could not open XML input");
    }
    $e=4096;
    $file_content = fread($fp, 5000000000);
    xml_parse($xml_parser, $file_content, feof($fp));
    echo "<pre>";
    print_r($valuess);
    if(is_array($valuess)){
      mysql_connect('********', '*****', '*******');
      mysql_select_db("wp534");
    for($i=0;$i<count($valuess);$i++)
    {
    $sql = "INSERT INTO wp_xmldata (RegistreringNummerNummer, KoeretoejMaerkeTypeNavn, KoeretoejModelTypeNavn, KoeretoejVariantTypeNavn, KoeretoejTypeTypeNavn, KoeretoejOplysningFoersteRegistreringDato, DrivkraftTypeNavn, SynResultatSynsDato) values ";
    $items=array();
    $valuesArr=array();    
    //echo ($i+1).'  ------------------------<br/>';
      for($j=0;$j<count($names[$i]);$j++)
      {  //echo $names[$i][$j].'=>'.$valuess[$i][$j]."</br>";
                $a=explode("ns:",$names[$i][$j]); 
                $items[$a[1]]=$valuess[$i][$j];
      }
                $valuesArr[] = "('$items[RegistreringNummerNummer]','$items[KoeretoejMaerkeTypeNavn]','$items[KoeretoejModelTypeNavn]','$items[KoeretoejVariantTypeNavn]','$items[KoeretoejTypeTypeNavn]','$items[KoeretoejOplysningFoersteRegistreringDato]','$items[DrivkraftTypeNavn]','$items[SynResultatSynsDato]')";
    $sql .= implode(',', $valuesArr);
    /******start code for append data**********/
    /*$select="select * from wp_xmldata where RegistreringNummerNummer = '$items[RegistreringNummerNummer]'";
    //echo $fetch11;
    $select_result=mysql_query($select);
    if(mysql_num_rows($select_result) == 0)
    { //echo $sql;
      mysql_query($sql);
    }*/
    /******end code for append data**********/
    //mysql_query($sql);
    //echo $sql; 
    }
        enter code here
    }
    xml_parser_free($xml_parser);
    fclose($fp);

有人有什么建议吗?

谢谢,Ankit Sanghvi

您的问题还不在于这里的XML解析器,更根本的是:

 $file_content = fread($fp, 5000000000);

AFAIK在PHP字符串的大小限制为2GB。您尝试在该字符串中获取50GB。这根本行不通。请查阅文档,哪些数据适合哪些数据类型。对于字符串,您可以在这里获得信息:

注意:字符串最大可达2GB(最大2147483647字节)

来源:http://php.net/manual/en/language.types.string.php

因此,您应该理解xml_parse必须而不是一次对整个字符串进行操作,它允许逐块解析。在这里,您应该阅读手册,了解这些函数的用法,然后编写代码。

尤其是你已经碰壁了。是时候更改代码并用拉取逻辑重写它了。或者,以XMLReader为例,可能扩展为XMLReaderIterator