在 PHP 中检测正确的字符编码?

Get*_*ree 5 php character-encoding detection multibyte

我正在尝试检测字符串的字符编码,但无法获得正确的结果。
例如:

$str = "€ ‚ ƒ „ …" ;
$str = mb_convert_encoding($str, 'Windows-1252' ,'HTML-ENTITIES') ;
// Now $str should be a Windows-1252-encoded string.
// Let's detect its encoding:
echo mb_detect_encoding($str,'Windows-1252, ISO-8859-1, UTF-8') ;
Run Code Online (Sandbox Code Playgroud)

该代码输出ISO-8859-1但它应该是Windows-1252.

这有什么问题?

编辑:
更新示例,以响应@raina77ow。

$str = "€‚ƒ„…" ; // no white-spaces
$str = mb_convert_encoding($str, 'Windows-1252' ,'HTML-ENTITIES') ;
$str = "Hello $str" ; // let's add some ascii characters
echo mb_detect_encoding($str,'Windows-1252, ISO-8859-1, UTF-8') ;
Run Code Online (Sandbox Code Playgroud)

我再次得到错误的结果。

rr-*_*rr- 0

尽管使用 ISO-8859-1 和 CP-1252 编码的字符串具有不同的字节码表示形式:

<?php
$str = "&euro; &sbquo; &fnof; &bdquo; &hellip;" ;
foreach (array('Windows-1252', 'ISO-8859-1') as $encoding)
{
    $new = mb_convert_encoding($str, $encoding, 'HTML-ENTITIES');
    printf('%15s: %s detected: %10s explicitly: %10s',
        $encoding,
        implode('', array_map(function($x) { return dechex(ord($x)); }, str_split($new))),
        mb_detect_encoding($new),
        mb_detect_encoding($new, array('ISO-8859-1', 'Windows-1252'))
    );
    echo PHP_EOL;
}
Run Code Online (Sandbox Code Playgroud)

结果:

Windows-1252: 802082208320842085 detected:            explicitly: ISO-8859-1
  ISO-8859-1: 3f203f203f203f203f detected:      ASCII explicitly: ISO-8859-1
Run Code Online (Sandbox Code Playgroud)

...从我们在这里可以看到, 的第二个参数似乎有问题mb_detect_encoding。使用mb_detect_order代替参数会产生非常相似的结果。