带有重音的希腊元音显示为两个字符而不是单个字符

Nic*_*Ath 0 java string character-encoding

我正在处理希腊语的输入,其中元音可以有重音

\n

我注意到包含带重音的元音的单词中有一些奇怪的输入,有时带重音的相同元音似乎是两个单独的字符,而其他时候带重音的相同元音似乎是一个字符,我猜不同的字符集编码对这种行为有罪。

\n

示例如下所示

\n

\xce\xb5\xcc\x81 -----> 是两个单独的字符,\xce\xb5\xcc\x81

\n

\xce\xad -----> 是单个字符\xce\xad

\n

我对上述行为的疑问如下:

\n
    \n
  1. 造成这种现象的根本原因是什么?
  2. \n
  3. 我怎样才能将所有这两个字符声调元音转换为单个字符声调元音?(例如将 \xce\xb5\xcc\x81 转换为 \xce\xad),是否有任何“全局方法”来处理此类编码问题?
  4. \n
\n

目前,作为解决方案,我所做的是将任何可能的两个字符元音替换为单个字符,如下所示:

\n
text = text.replaceAll("\xce\xb1\xcc\x81", "\xce\xac")\n        .replaceAll("\xce\xb5\xcc\x81", "\xce\xad")\n        .replaceAll("\xce\xb7\xcc\x81", "\xce\xae")\n        .replaceAll("\xce\xb9\xcc\x81", "\xce\xaf")\n        .replaceAll("\xcf\x85\xcc\x81", "\xcf\x8d")\n        .replaceAll("\xce\xbf\xcc\x81", "\xcf\x8c")\n        .replaceAll("\xcf\x89\xcc\x81", "\xcf\x8e")\n        .replaceAll("\xce\x91\xcc\x81", "\xce\x86")\n        .replaceAll("\xce\x95\xcc\x81", "\xce\x88")\n        .replaceAll("\xce\x97\xcc\x81", "\xce\x89")\n        .replaceAll("\xce\x99\xcc\x81", "\xce\x8a")\n        .replaceAll("\xce\xa5\xcc\x81", "\xce\x8e")\n        .replaceAll("\xce\x9f\xcc\x81", "\xce\x8c")\n        .replaceAll("\xce\xa9\xcc\x81", "\xce\x8f");\n
Run Code Online (Sandbox Code Playgroud)\n

但应该有更好的方法来实现这一点,我使用Java进行文本处理

\n

Gia*_*zzi 5

根本原因:有时有许多不同的方法用 Unicode 表示相同的字形。通常我们转换为规范形式,但有两种规范/规范化形式(分解:NFD 和组合:NFC)。Apple 更喜欢第一种(这是 Unicode 最初的首选方式),大多数其他操作系统更喜欢第二种。每种字体都有自己的偏好(但是 shaper 库会处理它)。

您可以将文本转换为规范的组合形式 (NFC),但并非所有字形都可以转换为单个字符:重音符号和基本字符的某种组合需要两个代码点(如果有多个重音符号则需要更多代码点)。


Swe*_*per 5

由于 Unicode 的复杂性,同一文本有多种编码方式。您可以使用锐音符号将 \xce\xb5 编码为单个字符“GREEK SMALL LETTER EPSILON WITH TONOS”(U+03AD),或编码为“GREEK SMALL LETTER EPSILON”(U+03B5) 后跟“COMBINING ACUTE ACCENT”( U+0301)。有时,不同的人和软件确实会对这些进行不同的编码。

\n

要转换为“更紧凑”的编码,您可以使用该类java.text.Normalizer规范化形式C (NFC)。

\n
// you can pass the entire string into this:\nNormalizer.normalize("\xce\xb5\\u0301", Normalizer.Form.NFC) // produces a string with a \\u03AD char\n
Run Code Online (Sandbox Code Playgroud)\n

不太紧凑的编码称为 NFD。

\n