Php readOuterXml(),输入不正确UTF-8,指示编码
我使用解析来自第三方的大型XML文件,文件大小为1GB+。XML文件将编码指定为UTF8(Php readOuterXml(),输入不正确UTF-8,指示编码,php,xml,utf-8,character-encoding,xmlreader,Php,Xml,Utf 8,Character Encoding,Xmlreader,我使用解析来自第三方的大型XML文件,文件大小为1GB+。XML文件将编码指定为UTF8(),尽管它不是 XMLReader由于未知的编码类型而引发错误,但直到它已经处理了文件的大部分内容 异常消息: 输入不正确UTF-8,表示编码不正确 我已经确定文件的实际编码是ISO-8859-1,如果我在调用$reader->open()时手动指定此编码,它将正常工作 问题是我的脚本需要解析数据库中的未知文件,因此它需要依赖文件中指定的编码类型。我需要找到一种方法来解析任何文件,而不管其编码是什么,有什么
),尽管它不是
XMLReader由于未知的编码类型而引发错误,但直到它已经处理了文件的大部分内容
异常消息:
输入不正确UTF-8,表示编码不正确
我已经确定文件的实际编码是ISO-8859-1
,如果我在调用$reader->open()
时手动指定此编码,它将正常工作
问题是我的脚本需要解析数据库中的未知文件,因此它需要依赖文件中指定的编码类型。我需要找到一种方法来解析任何文件,而不管其编码是什么,有什么建议吗?用于解析XML。为了避免编码问题,请在数据上使用。我发现这非常适合从一种编码转换为另一种编码
我的技巧是正常解析文件,当遇到编码错误时,只需使用vim重新编码文件并再次开始解析
以下是大概的想法:
$xmlFile = '/path/to/file.xml';
// Parse the file in a loop
while(...)
{
try
{
// Normal parsing logic...
$reader->readOuterXml();
//...
}
catch(Exception $ex)
{
$encoding = getXMLEncoding($xmlFile) ?: 'utf-8';
exec(sprintf(VIM_PATH . ' -c "set fileencoding=%s" -c "wq" "%s"', $encoding, $xmlFile));
// File has been re-encoded
// The real encoding should now match the declared encoding
// -> Go back to the beginning and parse the file again
}
}
使用此方法可能会乱码1或2个字符,但这比完全失败的解析要好得多。理想情况下,第三方将正确标记其文件
我的系统是Windows,所以vim参数在Linux上可能不同(不知道)。1)一个1GB的XML文件很难通过一次加载到内存中来解析。2) 通过
utf8\u encode
运行整个文件的问题基本相同。3) OP不知道文件的编码方式,因此utf8\u encode
在这里不是一个全面的解决方案。在解析文件之前,您必须确认文件的编码方式。因为你很难通过将文件读入内存来实现这一点,所以我建议你要么逐行读取并检查每一行,要么使用命令行工具,比如iconv
,它可以在不将文件全部读入内存的情况下进行检查。@deceze:谢谢你的建议,我找到并将使用它来检测编码。服务器是Windows,所以我必须先编译自己才能进行测试。