将PHP UTF-8转换为Windows命令行编码

14

问题很简单:我有一个用UTF-8编写的Php脚本。在这个脚本中,我想要做到以下几点:

  <?
  echo "âêïû\n";
  ?>

如果我在Windows提示符中运行它,我会得到这个结果:
C:\php>php -c C:\WINDOWS\php.ini -f mysqldump.php
âêïû
C:\php>

我一直找不到正确的转换方案。我也尝试了这段代码:

$tab = mb_list_encodings();
foreach ($tab as $enc1) {
  foreach ($tab as $enc2) {
    $t=mb_convert_encoding("âêïû\n", $enc1, $enc2);
    if (strlen($t)<14) {
      echo $enc1." ".$enc2." = ".$t."\n";
    }
  }
}

我找不到正确的转换方法!

非常感谢您的任何帮助。

4个回答

19

问题是Windows默认情况下不支持UTF8编码。根据这个链接,如果按照以下步骤进行操作:

  1. 打开命令提示符窗口
  2. 更改窗口属性以使用除默认光栅字体之外的其他字体,Lucida Console True Type字体效果很好。
  3. 在命令提示符中运行“chcp 65001”

你就可以输出UTF8编码了。


很好听到你可以在 shell 中更改编码。 - Peter Bailey
好的,我已经尝试了“chcp 65001”。现在每次运行“php -c C:\WINDOWS\php.ini -f mysqldump.php | more”时,都会出现“内存不足错误”。然后我尝试去掉“| more”(我猜这对Windows来说太冒险了,真气人),但是脚本在开始时就停止了... - Olivier Pons
你可以尝试一下只用 "echo 'hello world';" 吗? - Doug T.
3
请注意,Windows 命令行的默认字符集 不是 ISO-8859-1,而是 Windows-1252(至少对于 Latin1 / 西欧语言)。 - Stefan Gehrig
"chcp 65001" 是一种hack,不支持完整的UTF-8或多字节输入。 - Alastair McCormack

8

你让我走上了正确的道路,但是有一个问题(我喜欢Windows \o/):

C:\php>chcp 65001
Page de codes active : 65001
C:\php>php -c C:\WINDOWS\php.ini -f mysqldump.php | more
Mémoire insuffisante.

内存不足 = not enough memory。

如果我尝试

C:\php>chcp 1252
C:\php>php -c C:\WINDOWS\php.ini -f mysqldump.php
C:\php>ééîîïïÂÂÂÂâûü

它有效。只有上帝知道为什么。但它有效。感谢你让我找到了正确的方法!!

顺便说一下,将UTF8格式的PHP代码正确地输出到命令提示符的代码是:

  echo mb_convert_encoding($utf8_string, "pass", "auto");

1
上帝也不知道为什么! - markus
1
BTW附加到末尾让我省了很多麻烦,因为mb_convert_encoding($utf8_string, "pass", "auto")也是在Windows本地读/写UTF-8命名文件的方法。 - lalengua
@lalengua,第二个参数“pass”是什么意思?我只找到了第三个参数的“auto”: “auto”扩展为“ASCII,JIS,UTF-8,EUC-JP,SJIS”(c)php.net - vladkras
@vladkras 很难找到,但是你知道 mb_convert_encoding 函数执行了双重过程:首先解码字符串,然后再使用新编码重新编码。 在 PHP 的源代码中,pass 常量在此处被定义为 mbfl_no_encoding_pass,它意味着函数将返回一个(Unicode?)字符串,未经任何编码。 也许以后的某个过程会再次对其进行编码? 源图在此处 - lalengua

1

试试这个。它使用俄语编码工作,我希望它也能用于法语:

class ConsoleHelper
{
    /**
     * @var boolean
     */
    private static $isEncodingSet = false;

    /**
     * @param string $message
     * @return string
     */
    public static function encodeMessage($message)
    {
        $isWindows = (DIRECTORY_SEPARATOR == '\\');
        if ($isWindows) {
            if ( ! self::$isEncodingSet) {
                shell_exec('chcp 866');
                self::$isEncodingSet = true;
            }
            $message = iconv('utf-8', 'cp866', $message);
        }
        return $message;
    }
}

你正在使用 866,我猜法语应该是 1252。不管怎样,我在6年前放弃了Windows,我很高兴我已经永远转向了Linux Mint(当然除了一些游戏)。客套话地说,Windows不再是我的菜。当然,当我谈论它时,我更加粗鲁。在这里,礼貌很重要 **<8^D**。 - Olivier Pons
对于法语来说,它是cp850。 - Maxence

0

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接