使用PHP读取XML时处理编码错误

使用PHP读取XML时处理编码错误,php,xml,encoding,Php,Xml,Encoding,我正在使用XMLReader解析来自第三方的XML。文件应该是UTF-8,但我得到了以下错误: 解析器错误:输入不正确UTF-8,请指示编码 字节:第166行C:\file.php中的0x11 0x72 0x20 0x41 在notepad++中查看XML文件,很清楚是什么导致了这种情况:有问题的行中包含一个控制字符 XML文件是由第三方提供的,我无法可靠地解决这个问题/确保将来不会发生这种情况。有人能推荐一个处理这个问题的好方法吗?我只想去掉控制字符——在这种特殊情况下,从XML文件中删除它就

我正在使用XMLReader解析来自第三方的XML。文件应该是UTF-8,但我得到了以下错误:

解析器错误:输入不正确UTF-8,请指示编码

字节:第166行C:\file.php中的0x11 0x72 0x20 0x41

在notepad++中查看XML文件,很清楚是什么导致了这种情况:有问题的行中包含一个控制字符


XML文件是由第三方提供的,我无法可靠地解决这个问题/确保将来不会发生这种情况。有人能推荐一个处理这个问题的好方法吗?我只想去掉控制字符——在这种特殊情况下,从XML文件中删除它就可以了——但我担心,一直这样做可能会导致无法预见的问题。谢谢。

为什么第三方不能可靠地解决此问题?如果他们的XML中有非法字符,我敢打赌这是一个有效的问题


话虽如此,为什么不先删除字符,然后再使用?

如果字符串是有效的UTF-8,您可以使用
str\u replace()
。请注意,
str_replace()
随后将处理字节偏移量,因此您不再处理PHP字符串,而是处理字节字符串

还有一个问题:如果您的第三方包含在XML中没有任何用途的随机空白和控制字符,那么您最好假设它们最终会破坏UTF-8。因此,在您确定他们当前的垃圾并非完全无用之前,您不能满怀信心地使用
str_replace()

也许您可以选择一个快捷方式,将其填充到libxml DOMDocument对象中,并使用@抑制错误,让libxml库处理错误。比如:

$doc = new DOMDocument();
if(@$doc->loadXML($raw_string)) {
  // document is loaded. time to normalize() it.
}
else {
  throw new Exception("This data is junk");
}

为什么您和第三方用XML交换数据?大概双方都希望通过使用XML而不是一些随机的专有格式来获得一些好处。如果您允许他们生成不好的XML(我更愿意称之为非XML),那么双方都不会得到这些好处。改过自新符合他们的利益。试着让他们相信这一点。

第三方是一家大型公司,通过RSS提要提供XML,并通过电子邮件向他们发送通用的“我们会回复你”。此外,如果他们犯了一次这样的错误,那么我会谨慎地犯错误,并假设无论他们说什么,这种错误都可能再次发生。啊,我明白了(并且同意前瞻性思维)。
str\u replace
是否适用于预解析?使用str\u replace(或类似)是一个选项。但我对unicode了解不多,也不确定有多少像这样的潜在问题字符。如果有很多,效率可能会成为一个问题,因为XML文件很大(>100MB)。或者,您可以实现自己的解析器,并在解析每行时去除字符(存储在数组中的非法字符)。除非公司愿意修复他们的bug,否则无论哪种方式,您都会有一定的开销。在UTF-8流中使用代码点U+0011、设备控制1或控制-R不是非法的,甚至不是不合适的UTF-8。就Unicode而言,这是一个完全有效的代码点。XML可能是另一回事。您可能会从中受益