如何在 Windows 命令行上使用 Unicode 字符?

How can I use Unicode characters on the Windows command line?

提问人:Vilx- 提问时间:12/23/2008 最后编辑:Peter MortensenVilx- 更新时间:8/23/2023 访问量:555957

问:

我们在 Team Foundation Server (TFS) 中有一个项目,其中包含一个非英语字符 (š)。在尝试编写一些与构建相关内容的脚本时,我们偶然发现了一个问题;我们不能将 š 字母传递给命令行工具。命令提示符或其他命令会搞砸它,并且 tf.exe 实用程序找不到指定的项目。

我已经尝试了不同的 .bat 文件格式(ANSI、带和不带 BOMUTF-8)以及用 JavaScript(本质上是 Unicode)编写脚本,但没有运气。如何执行程序并向其传递 Unicode 命令行?

Unicode 命令行 输入 Windows-控制台

评论

2赞 JinSnow 1/14/2017
Python 3.6:“Windows 上的默认控制台接受该版本的所有 Unicode 字符”(嗯,大部分对我来说)但是您需要配置控制台:右键单击窗口顶部(cmd 或 python IDLE),在默认/字体中选择“Lucida 控制台”。
0赞 phuclv 5/28/2017
在 Windows 控制台应用中输出 unicode 字符串在 Windows 中使用 C++ 将 Unicode 输出到控制台
0赞 phuclv 5/28/2017
如何在 Windows 控制台上输出 Unicode 字符串的可能重复项
2赞 Vilx- 5/28/2017
@LưuVĩnhPhúc - 不,这是关于传递 unicode 命令行参数,而不是在控制台中显示文本。控制台可能根本不参与其中。
0赞 Henke 1/31/2023
相关。• 什么编码让 Å Ä Ö 工作 • 在命令提示符下使用 UTF-8 编码 (CHCP 65001) • 如何在 Windows 命令行中使用 Unicode 字符 • CHCP 65001 和 .bat 文件使瑞典语字符在 Windows 命令提示符中正确显示

答:

432赞 kgiannakakis 12/23/2008 #1

尝试:

chcp 65001

这会将代码页更改为 UTF-8。此外,您需要使用 Lucida 控制台字体。

评论

97赞 bobince 12/30/2011
请注意,Windows 的代码页 65001 支持中存在严重的实现错误,这将破坏许多依赖 C 标准库 IO 方法的应用程序,因此这是非常脆弱的。(批处理文件在 65001 中也停止工作。不幸的是,UTF-8 在 Windows 中是二等公民。
10赞 Roman Starkov 12/3/2012
@bobince 是否有 Windows 代码页 65001 支持中的错误示例?我很好奇,因为我从来没有遇到过,谷歌搜索也没有发现任何东西。(当然,批处理文件确实会停止工作,但 UTF-8 几乎不是二等公民......
24赞 bobince 12/4/2012
@romkyns:我的理解是,返回字节数的调用(例如 fread/fwrite/etc)实际上返回字符数。这会导致各种各样的症状,例如输入读取不完整、fflush 挂起、批处理文件损坏等。一些背景。用于 CJK“多字节”语言环境的默认代码页内置了特殊处理功能来修复此问题,但 65001 没有 - 不支持。
5赞 alexchandel 9/11/2015
更新了 Kaplan 博客 关于 Windows 中损坏的 UTF-8 可在此处获得,因为 Microsoft 在他以错误的方式摩擦高层后删除了他所有的博客文章。
8赞 Eryk Sun 3/6/2017
控制台对代码页 65001 的 (conhost.exe) 支持从根本上中断(对于 Windows 7 中的输入和输出,但对于 Windows 10 中的输入仍然中断)。请删除此建议,以避免在天真的“帮助”的无休止循环中重复这个糟糕的建议。cmd shell 是一个 Unicode 应用程序,它使用控制台的 UTF-16 API 和基本 API 和 .如果处理命令行时出现问题,那是因为应用程序使用的是标准 C 中的 ANSI 编码版本,而不是入口点中的 。CreateProcessWShellExecuteExWchar *mainwchar_t *wmain
14赞 User 4/14/2009 #2

实际上,诀窍在于命令提示符实际上可以理解这些非英语字符,只是无法正确显示它们。

当我在命令提示符下输入包含一些非英语字符的路径时,它显示为“?? ?????? ?????”。当您提交命令时(在我的情况下为 cd“??? ?????? ?????”),一切都按预期工作。

41赞 vanna 8/24/2010 #3

我有同样的问题(我来自捷克共和国)。我有一个英文版的 Windows 安装,我必须处理共享驱动器上的文件。文件的路径包括特定于捷克语的字符。

对我有用的解决方案是:

在批处理文件中,更改字符集页

我的批处理文件:

chcp 1250
copy "O:\VEŘEJNÉ\ŽŽŽŽŽŽ\Ž.xls" c:\temp

批处理文件必须保存在 CP 1250 中。

请注意,控制台不会正确显示字符,但它会理解它们......

3赞 Christoforos 12/2/2012 #4

对于类似的问题,(我的问题是在命令提示符下显示MySQL中的UTF-8字符),

我是这样解决的:

  1. 我将命令提示符的字体更改为Lucida Console。(此步骤必须与您的情况无关。它只与你在屏幕上看到的内容有关,而与真正的角色无关)。

  2. 我将代码页更改为 Windows-1253。您可以通过“chcp 1253”在命令提示符下执行此操作。它适用于我想看到 UTF-8 的情况。

评论

9赞 Vilx- 12/2/2012
Windws-1253 不是 Unicode 代码页。这是一个标准的 256 个字符的代码页。显然,您只使用了可以在该代码页中显示的字符,但它不会是通用的。
33赞 Maxim Yefremov 4/7/2013 #5

检查非 Unicode 程序的语言。如果您在 Windows 控制台中使用俄语有问题,那么您应该在此处设置俄语:

Changing language for non-Unicode programs

评论

8赞 ivan_pozdeev 10/28/2017
这不会启用对 Unicode 的支持,它只会将默认代码页切换为仍然是 8 位字符集。它甚至使用而不是它增加了自己的麻烦。cmdcp866cp866cp1251
1赞 Mike Beckerle 5/31/2013 #6

一个更好的更干净的做法:只需安装可用的免费 Microsoft 日语语言包。(其他东方语言包也可以使用,但我已经测试了日语语言包。

这为您提供了具有较大字形集的字体,使它们成为默认行为,更改了各种 Windows 工具,如 cmd、写字板等。

1赞 madhav bitra 2/12/2015 #7

将代码页更改为 1252 对我有用。对我来说,问题是符号 double doller § 正在 Windows Server 2008 上通过 DOS 转换为另一个符号。

我在 BCP 声明中使用了 CHCP 1252 和它前面的上限 ^§。

3赞 S. Hristov 4/9/2015 #8

如果您的计算机在DOS窗口中键入路径/文件名时正确显示路径/文件名,则可以快速决定.bat文件:

  1. 复制温度.txt [按 Enter]
  2. 键入路径/文件名 [按 Enter]
  3. Ctrl-Z [按 Enter]

这样,您可以创建一个 .txt 文件 - temp.txt。在记事本中打开它,复制文本(不用担心它看起来不可读)并将其粘贴到您的 .bat 文件中。 在DOS窗口中以这种方式执行.bat对mе(西里尔文,保加利亚语)有效。

16赞 Wernfried Domscheit 11/2/2015 #9

更改 Windows 控制台的默认代码页非常困难。当您搜索网络时,您会发现不同的建议,但是其中一些可能会完全破坏您的 Windows,即您的 PC 不再启动。

最安全的解决方案是这样的: 转到注册表项并添加 String value = 。HKEY_CURRENT_USER\Software\Microsoft\Command ProcessorAutorunchcp 65001

或者,您可以将这个小型批处理脚本用于最常见的代码页。

@ECHO off

SET ROOT_KEY="HKEY_CURRENT_USER"


FOR /f "skip=2 tokens=3" %%i in ('reg query HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Nls\CodePage /v OEMCP') do set OEMCP=%%i

ECHO System default values:

ECHO.
ECHO ...............................................
ECHO Select Codepage 
ECHO ...............................................
ECHO.
ECHO 1 - CP1252
ECHO 2 - UTF-8
ECHO 3 - CP850
ECHO 4 - ISO-8859-1
ECHO 5 - ISO-8859-15
ECHO 6 - US-ASCII
ECHO.
ECHO 9 - Reset to System Default (CP%OEMCP%)
ECHO 0 - EXIT
ECHO.


SET /P  CP="Select a Codepage: "

if %CP%==1 (
    echo Set default Codepage to CP1252
    reg add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 1252>nul" /f
) else if %CP%==2 (
    echo Set default Codepage to UTF-8
    reg add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 65001>nul" /f
) else if %CP%==3 (
    echo Set default Codepage to CP850
    reg add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 850>nul" /f
) else if %CP%==4 (
    echo Set default Codepage to ISO-8859-1
    add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 28591>nul" /f
) else if %CP%==5 (
    echo Set default Codepage to ISO-8859-15
    add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 28605>nul" /f
) else if %CP%==6 (
    echo Set default Codepage to ASCII
    add "%ROOT_KEY%\Software\Microsoft\Command Processor" /v Autorun /t REG_SZ /d "@chcp 20127>nul" /f
) else if %CP%==9 (
    echo Reset Codepage to System Default
    reg delete "%ROOT_KEY%\Software\Microsoft\Command Processor" /v AutoRun /f
) else if %CP%==0 (
    echo Bye
) else (
    echo Invalid choice
    pause
)

使用而不是禁止显示每次启动新命令行窗口时都会得到的输出“活动代码页:65001”。@chcp 65001>nulchcp 65001

可从代码页标识符获取的所有可用编号的完整列表

请注意,这些设置将仅适用于当前用户。如果您想为所有用户设置它,请将行替换为SET ROOT_KEY="HKEY_CURRENT_USER"SET ROOT_KEY="HKEY_LOCAL_MACHINE"

1赞 Michael 12/2/2015 #10

我解决了一个类似的问题,即通过在批处理文件中用它们的短(8 点 3)名称引用它们来删除以 Unicode 命名的文件。

短名称可以通过执行 .显然,这仅适用于已知的 Unicode 文件名。dir /x

9赞 Steve Barnes 1/2/2016 #11

一个非常简单的选择是安装一个 Windows bash shell,例如 MinGW 并使用它:

Enter image description here

由于您需要使用 Unix 命令行功能,因此需要一点学习曲线,但您会喜欢它的强大功能,并且您可以将控制台字符集设置为 UTF-8。

Enter image description here

当然,您还可以获得所有常用的 *nix 好东西,例如 grep、find、less 等。

6赞 Aaron3468 4/7/2016 #12

由于我还没有看到 Python 2.7 的任何完整答案,我将概述两个重要步骤和一个非常有用的可选步骤。

  1. 您需要一种支持 Unicode 的字体。Windows 自带 Lucida 控制台,可以通过右键单击命令提示符的标题栏并单击该选项来选择。这也提供了对颜色的访问。请注意,还可以通过选择来更改以某种方式调用的命令窗口的设置(例如,在此处打开,Visual Studio)。DefaultsProperties
  2. 您需要将代码页设置为 ,这似乎是 Microsoft 尝试为命令提示符提供 UTF-7 和 UTF-8 支持。为此,请在命令提示符下运行 chcp 65001。设置后,它会一直保持这种状态,直到窗口关闭。每次启动 cmd.exe 时都需要重做此操作。cp65001

有关更永久的解决方案,请参阅超级用户上的此答案。简而言之,使用 regedit at 创建一个 (String) 条目并将其命名为 。将其值更改为 。如果不想看到命令的输出消息,请改用。REG_SZHKEY_LOCAL_MACHINE\Software\Microsoft\Command ProcessorAutoRunchcp 65001@chcp 65001>nul

一些程序在与这种编码交互时遇到麻烦,MinGW 是一个值得注意的程序,它在编译时会失败,并显示无意义的错误消息。尽管如此,这工作得很好,不会导致大多数程序出现错误。

15赞 Alon Or 8/1/2016 #13

在 Windows 10 x64 计算机上,我通过以下方式使命令提示符显示非英语字符:

打开提升的命令提示符(以管理员身份运行 CMD.EXE)。通过以下方式向控制台查询注册表中的可用 TrueType 字体:

    REG query "HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Console\TrueTypeFont"

你将看到如下输出:

    0    REG_SZ    Lucida Console
    00    REG_SZ    Consolas
    936    REG_SZ    *新宋体
    932    REG_SZ    *MS ゴシック

现在我们需要添加一个支持您需要的字符的 TrueType 字体,例如 Courier New。我们通过在字符串名称中添加零来做到这一点,因此在本例中,下一个将是“000”:

    REG ADD "HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Console\TrueTypeFont" /v 000 /t REG_SZ /d "Courier New"

现在我们实现 UTF-8 支持:

    REG ADD HKCU\Console /v CodePage /t REG_DWORD /d 65001 /f

将默认字体设置为“Courier New”:

    REG ADD HKCU\Console /v FaceName /t REG_SZ /d "Courier New" /f

将字体大小设置为 20:

    REG ADD HKCU\Console /v FontSize /t REG_DWORD /d 20 /f

如果您喜欢,请启用快速编辑:

    REG ADD HKCU\Console /v QuickEdit /t REG_DWORD /d 1 /f

评论

5赞 Eryk Sun 9/9/2017
通常,使用代码页 65001 只能在 Windows 10 和 Creators 更新中工作,而不会出现错误。在 Windows 7 中,它将同时具有输出和输入错误。在 Windows 8 和旧版本的 Windows 10 中,它只有输入错误,将输入限制为 7 位 ASCII。
0赞 Green 10/18/2020
我尝试使用这种方法,现在字体超级小,似乎是永久性的。
5赞 code4j 1/22/2017 #14

这个问题很烦人。我的文件名和文件内容中通常有汉字。请注意,我使用的是 Windows 10,这是我的解决方案:

显示文件名,例如,如果您在 Windows 10 上安装了 Ubuntu bashdirls

  1. 将区域设置为支持非 utf 8 字符。

  2. 之后,控制台的字体将更改为该区域设置的字体,并且还会更改控制台的编码。

完成上述步骤后,要使用命令行工具显示 UTF-8 文件的文件内容

  1. 将页面更改为 utf-8chcp 65001
  2. 更改为支持 utf-8 的字体,例如 Lucida 控制台
  3. 使用命令查看文件内容,或者如果您在 Windows 10 上安装了 Ubuntu bashtypecat
  4. 请注意,将控制台的编码设置为 utf-8 后,我无法使用中文输入法在 cmd 中输入中文字符。

最懒惰的解决方案:只需使用控制台模拟器,例如 http://cmder.net/

102赞 Ilya Zakharevich 12/16/2017 #15

我的背景:我多年来一直在控制台中使用Unicode输入/输出(并且每天都经常这样做。此外,我为这项任务开发了支持工具)。就您了解以下事实/限制而言,问题很少:

  • CMD和“控制台”是不相关的因素。 只是准备在控制台(“控制台应用程序”)中“工作”的程序之一。CMD.exe
  • AFAIK,对Unicode有完美的支持;当任何代码页处于活动状态时,您可以输入/输出所有 Unicode 字符。CMD
  • Windows的控制台对Unicode有很多支持,但它并不完美(只是“足够好”;见下文)。
  • chcp 65001非常危险。除非一个程序是专门为解决 Windows API 中的缺陷而设计的(或者使用具有这些解决方法的 C 运行时库),否则它将无法可靠地工作。Windows 8 修复了 cp65001 中 1/2 的问题,但其余问题仍适用于 Windows 10
  • 我在 Windows-1252 中工作。正如我已经说过的:要在控制台中输入/输出Unicode,不需要设置代码页

细节

  • 若要将 Unicode 读/写到控制台,应用程序(或其 C 运行时库)应足够智能,以便不使用 API,而是使用 API。(有关示例,请参阅 Python 如何做到这一点File-I/OConsole-I/O
  • 同样,要读取 Unicode 命令行参数,应用程序(或其 C 运行时库)应该足够智能,可以使用相应的 API。
  • 控制台字体呈现仅支持 BMP 中的 Unicode 字符(换句话说:下面)。只支持简单的文本呈现(因此,只要使用预组合形式,欧洲和一些东亚语言应该可以正常工作)。这里有一个东亚和字符 U+0000、U+0001、U+30FB 的 [次要] 细则U+10000

实际考虑因素

  • Window 上的默认值不是很有帮助。为了获得最佳体验,应调整三部分配置:

    • 对于输出:全面的控制台字体。为了获得最佳效果,我推荐我的构建。(安装说明在此处提供,并且也列在本页的其他答案中。
    • 对于输入:一个有能力的键盘布局。为了获得最佳效果,我推荐我的布局
    • 对于输入:允许Unicode的十六进制输入
  • “粘贴”到控制台应用程序中的另一个问题(非常技术性):

    • 十六进制输入在 KeyUp 上提供 ;所有其他提供角色的方式都发生在 KeyDown 上;因此,许多应用程序还没有准备好在 KeyUp 上看到字符。(仅适用于使用 Console-I/O API 的应用程序。Alt
    • 结论:许多应用程序不会对十六进制输入事件做出反应。
    • 此外,“粘贴”字符会发生什么取决于当前的键盘布局:如果可以在不使用前缀键的情况下键入该字符(但使用任意复杂的修饰符组合,如 + + + + + ),那么它就会在模拟按键时传递。这是任何应用程序所期望的 - 因此粘贴仅包含此类字符的任何内容都可以。CtrlAltAltGrKanaShiftGray
    • 但是,“其他”字符是通过模拟十六进制输入来传递的。

    结论:除非您的键盘布局支持输入大量没有前缀键的字符,否则当您通过控制台的 UI 时,某些有问题的应用程序可能会跳过字符:+ , + .(这就是为什么我建议使用我的键盘布局!PasteAltSpaceEP

人们还应该记住,Windows 的“替代的、'功能更强大'的游戏机”根本不是游戏机。它们不支持控制台 I/O API,因此依赖这些 API 工作的程序将无法运行。(不过,仅使用“将 File-I/O API 用于控制台文件句柄”的程序可以正常工作。

这种非控制台的一个例子是 Microsoft 的 PowerShell 的一部分。我不使用它;要进行实验,请按下并松开 ,然后键入 。Windows keypowershell


(另一方面,有些程序,如ConEmuANSICON,试图做更多的事情:它们“尝试”拦截控制台I/O API,使“真正的控制台应用程序”也能工作。这绝对适用于玩具示例程序;在现实生活中,这可能会也可能不会解决您的特定问题。实验。

总结

  • 设置字体、键盘布局(以及可选的允许十六进制输入)。

  • 仅使用通过控制台 I/O API 并接受 Unicode 命令行参数的程序。例如,任何 Cygwin 编译的程序都应该没问题。正如我已经说过的,CMD也很好。

更新:最初,对于 中的一个错误,我混淆了内核层和 CRTL 层(更新 2:和 Windows 用户模式 API!也:Windows 8 修复了此错误的一半;我澄清了有关“更好的控制台”应用程序的部分,并添加了对 Python 如何做到这一点的引用。cp65001

2赞 Robert Boehne 8/31/2018 #16

我在这里看到了几个答案,但它们似乎没有解决问题——用户希望从命令行获取 Unicode 输入。

Windows 使用 UTF-16 在两个字节字符串中进行编码,因此您需要从程序中的操作系统获取这些字符串。有两种方法可以做到这一点——

  1. Microsoft 有一个扩展,允许 main 采用宽字符数组: int wmain(int argc, wchar_t *argv[]);https://msdn.microsoft.com/en-us/library/6wd819wh.aspx

  2. 调用 Windows API 以获取命令行的 Unicode 版本 wchar_t win_argv = (wchar_t)CommandLineToArgvW(GetCommandLineW(), &nargs);CommandLineToArgvW 函数 (shellapi.h)

有关详细信息,请阅读 UTF-8 Everywhere,尤其是在支持其他操作系统的情况下。

评论

1赞 Vilx- 8/31/2018
啊,不,对不起,但你错过了这个问题。这是当我编写一个将接收 unicode 字符的程序时。我的问题是关于将 unicode 字符发送到另一个程序(希望它支持接收它们,但除了反汇编之外我真的没有办法知道)。
9赞 zvi 4/14/2019 #17

我发现这种方法在新版本的 Windows 10 中很有用:

打开此功能:“Beta:使用 Unicode UTF-8 提供全球语言支持”

控制面板 -> 区域设置 -> 管理选项卡->更改 系统区域设置...

Region Settings

评论

4赞 Alon Or 1/26/2021
请注意这一点,它破坏了一些在 Server 2019 中运行良好的旧程序的功能。
7赞 VonC 5/7/2019 #18

从 2019 年 6 月开始,使用 Windows 10 时,无需更改代码页。

请参阅“Windows 终端简介”(来自 Kayla Cinnamon)和 Microsoft/终端
通过使用 Consolas 字体,将提供部分 Unicode 支持。

Microsoft/Terminal 问题 387 中所述:

Unicode 目前有 87,887 个表意文字。你也需要所有这些吗?
我们需要一个边界,超出该边界的字符应该通过字体回退/字体链接/其他方式来处理。

Consolas 应涵盖的内容:

  • 用作 CLI 中现代 OSS 程序使用的符号的字符。
  • 这些角色应遵循 Consolas 的设计和指标,并与现有的 Consolas 角色正确对齐。

Consolas 不应涵盖的内容:

  • 除了拉丁文、希腊文和西里尔文之外,字符和标点符号,尤其是需要复杂塑造的字符(如阿拉伯语)。
  • 这些字符应使用字体回退进行处理。
0赞 afkjm 6/6/2022 #19

请注意,对于那些使用 WSL 的人,他们也不希望来自 Cygwin 或 Git 的额外包,wsltty 是可用的,它只提供具有 UTF-8 支持的终端。