Go Unicode组合字符(grapheme群集)和MS Windows Console cmd.exe

Go Unicode组合字符(grapheme群集)和MS Windows Console cmd.exe,go,unicode,windows-10,windows-console,Go,Unicode,Windows 10,Windows Console,在下面的代码中,ủ不是单个Unicode字符u+00FC,而是由两个Unicode字符组成的单个字组,普通ASCIIuu+0075后跟组合分隔符u+0308 fmt.Println(“JủrgenDžemal”) fmt.Println(“Ju\u0308rgen\u01c5emel”) 如果我运行它,它将按预期工作 如果我在MS Windows 10“命令提示符”窗口中运行它,它不会直观地将组合字符与前一个字符组合在一起。 但是,当我将文本剪切并粘贴到此处时,它会正确显示: C:\>ver

在下面的代码中,
不是单个Unicode字符u+00FC,而是由两个Unicode字符组成的单个字组,普通ASCII
u
u+0075后跟组合分隔符u+0308

fmt.Println(“JủrgenDžemal”)
fmt.Println(“Ju\u0308rgen\u01c5emel”)
如果我运行它,它将按预期工作

如果我在MS Windows 10“命令提示符”窗口中运行它,它不会直观地将组合字符与前一个字符组合在一起。 但是,当我将文本剪切并粘贴到此处时,它会正确显示:

C:\>ver
Microsoft Windows[版本10.0.17134.228]
C:\>测试
朱尔根·艾马尔
朱尔根·埃梅尔
在屏幕上,在“命令提示符”窗口中,它看起来更像:

Ju–rgenDžemel
将代码页(chcp)从850更改为65001没有任何区别。更改字体(控制台、信使等)没有任何区别

过去我遇到过一些问题,基本上是因为Microsoft要求Windows程序使用不同的API将字符输出到标准输出,这取决于标准输出是附加到控制台还是附加到文件。我不知道这是否是同一问题的不同表现

我可以做些什么来正确显示这个Unicode grapheme集群吗?

如和所述

  • Windows控制台(conhost.exe)不支持组合代码。您必须首先规范化为使用预合成字符的等效字符串
  • 您可以使用
    golang.org/x/text/unicode/norm
    进行规范化(例如
    norm.NFC.String(“Ju̇rgenDžemal”)
我试过这个

s := "Ju\u0308rgen \u01c5emel"
fmt.Println(s)              // dieresis not combined with u by conhost.exe
s = norm.NFC.String(s)
fmt.Println(s)              // shows correctly
输出结果如下所示

或者,对于有着极其复杂的屏幕阅读器的视障人士——有点像这样:

Ju¨rgen Džemel
Jürgen Džemel
请注意,Unicode有四种不同的标准化形式,但NFC在互联网上的网页中使用最多,也适用于这种情况

此包中还有其他方法可能更有效或更有用

我读到有一些视觉字符在使用中,它们只能用Unicode组合字符来表示。换句话说,没有预合成字符。需要采取更彻底的办法来处理这些问题。从本质上讲,Unicode(或者更准确地说是人类语言及其版式)的复杂性几乎是永无止境的。有时候我觉得是这样的

参考资料

  • 例如,立陶宛文书写中使用的几个字符具有双重变音符号,因为它们只有分解形式。一个例子是小写的U加上macron和tilde(“ū̃”,U+016b U+0303,其中第一个代码点是小写的U加上macron,第二个是组合的锐重音)


Windows控制台(conhost.exe)不支持组合代码。您必须首先将标准化为使用预合成字符的字符串。@eryksun:谢谢,这看起来是个答案……如果您还没有找到这个答案:您可以使用来进行标准化(例如,
norm.NFC.String(“Ju∗rgenDžemal”)
;不确定哪一个适用于Windows)。@Peter:我只是在玩这个,谢谢(它可以)。如果你们中的一个没有发布答案,我会发布一个社区维基答案,引用你们两个。如果一个角色没有预编译的代码单元,那么控制台就不能显示它。控制台也不能显示复杂的脚本,不能混合半宽和全宽图示符(至少不能很好),也不能支持自动回退字体(可以手动配置回退)。这些限制是由于控制台使用的传统GDI功能可以追溯到WindowsNT3.1(1993)的第一个版本。微软负责控制台的团队暗示,计划基于DirectWrite进行重新设计。