15

StackOverflow 上有很多问题和答案,假设“字母”可以在正则表达式中匹配[a-zA-Z]。然而,对于 Unicode,还有更多的字符被大多数人视为字母(所有的希腊字母、Cyrllic .. 等等。Unicode 定义了许多块,每个块都可能有“字母”。

Java 定义为诸如字母字符之类的东西定义了 Posix 类 ,但它被指定为仅适用于 US-ASCII。预定义的字符类定义了由 组成的单词[a-zA-Z_0-9],它也排除了许多字母。

那么如何正确匹配 Unicode 字符串呢?有没有其他图书馆可以做到这一点?

4

3 回答 3

16

在这里你有一个很好的解释:

http://www.regular-expressions.info/unicode.html

一些提示:

“不幸的是,Java 和 .NET 不支持\X(尚)。\P{M}\p{M}*用作替代品。要匹配任意数量的字素,请使用(?:\P{M}\p{M}*)+代替\X+.”

"In Java, the regex token \uFFFF only matches the specified code point, even when you turned on canonical equivalence. However, the same syntax \uFFFF is also used to insert Unicode characters into literal strings in the Java source code. Pattern.compile("\u00E0") will match both the single-code-point and double-code-point encodings of à, while Pattern.compile("\\u00E0") matches only the single-code-point version. Remember that when writing a regex as a Java string literal, backslashes must be escaped. The former Java code compiles the regex à, while the latter compiles \u00E0. Depending on what you're doing, the difference may be significant."

于 2011-03-15T17:16:33.227 回答
5

您是在谈论 Unicode 类别,例如字母吗?这些由形式的正则表达式匹配\p{CAT},其中“CAT”是L任何字母的类别代码,或者是Lu大写或Lt标题大小写的子类别。

于 2011-03-15T17:13:20.057 回答
2

引用java.util.regex.Pattern的 JavaDoc 。

Unicode 支持

此类符合 Unicode 技术标准 #18 的第 1 级:Unicode 正则表达式指南,以及 RL2.1 规范等效项。

Unicode 转义序列(如 Java 源代码中的 \u2014)按照 Java 语言规范第 3.3 节中的描述进行处理。此类转义序列也由正则表达式解析器直接实现,因此 Unicode 转义可用于从文件或键盘读取的表达式中。因此,字符串 "\u2014" 和 "\\u2014" 虽然不相等,但编译成相同的模式,匹配十六进制值为 0x2014 的字符。

Unicode 块和类别是用 Perl 中的 \p 和 \P 结构编写的。如果输入具有属性 prop,则 \p{prop} 匹配,而如果输入具有该属性,则 \P{prop} 不匹配。块用前缀 In 指定,如 InMongolian。可以使用可选前缀 Is 指定类别:\p{L} 和 \p{IsL} 都表示 Unicode 字母的类别。块和类别可以在字符类的内部和外部使用。

支持的类别是由 Character 类指定的版本中的 Unicode 标准的类别。类别名称是标准中定义的名称,包括规范性和信息性。Pattern 支持的块名称是 UnicodeBlock.forName 接受和定义的有效块名称。

于 2011-03-15T17:15:43.417 回答