我想检测一些文本的编码(使用PHP).为此,我使用mb_detect_encoding()函数.
问题是如果我用mb_detect_order()函数改变可能的编码顺序,函数会返回不同的结果.
请考虑以下示例
$html = <<< STR ????????????????????????????????????????????????????????????????????????????????????????????????????????? STR; mb_detect_order(array('UTF-8','EUC-JP', 'SJIS', 'eucJP-win', 'SJIS-win', 'JIS', 'ISO-2022-JP','ISO-8859-1','ISO-8859-2')); $originalEncoding = mb_detect_encoding($str); die($originalEncoding); // $originalEncoding = 'UTF-8'
但是,如果您更改mb_detect_order()中的编码顺序,结果将会有所不同:
mb_detect_order(array('EUC-JP','UTF-8', 'SJIS', 'eucJP-win', 'SJIS-win', 'JIS', 'ISO-2022-JP','ISO-8859-1','ISO-8859-2')); die($originalEncoding); // $originalEncoding = 'EUC-JP'
所以我的问题是:
为什么会这样?
PHP中有没有一种方法可以正确无误地检测文本的编码?
这就是我期望发生的事情.
检测算法可能只是按顺序继续尝试您指定的编码mb_detect_order
,然后返回字节流有效的第一个编码.
更智能的东西需要统计方法(我认为通常使用机器学习).
编辑:有关更智能的方法,请参阅本文.
由于其重要性,自动字符集检测已经在主要的Internet应用程序(如Mozilla或Internet Explorer)中实现.它们非常准确和快速,但实施在个案基础上应用了许多领域特定的知识.与他们的方法相反,我们的目标是一个简单的算法,可以统一应用于每个字符集,并且该算法基于完善的标准机器学习技术.我们还研究了语言和字符集检测之间的关系,并比较了基于字节的算法和基于字符的算法.我们使用朴素贝叶斯(NB)和支持向量机(SVM).
并不是的.不同的编码通常具有大的重叠区域,如果您正在测试的字符串在该重叠内部存在,则两种编码都是可接受的.
例如,utf-8和ISO-8859-1对于字母az是相同的.字符串"hello"在两种编码中都具有相同的字节序列.
这正是为什么首先有一个mb_detect_order()
功能,因为它允许你说出这些冲突发生时你更喜欢发生什么.你想"你好"是utf-8还是ISO-8859-1?