3

在 C# 中,在大多数情况下似乎GrüsseGrüße被认为是平等的,正如这个漂亮的网页所解释的那样。我试图在 Java 中找到类似的行为 - 显然不是在java.lang.String.

我以为我很幸运java.regex.PatternPattern.UNICODE_CASE. Javadoc 说:

UNICODE_CASE 启用 Unicode 感知大小写折叠。如果指定了此标志,那么在由 CASE_INSENSITIVE 标志启用时,不区分大小写的匹配将以符合 Unicode 标准的方式进行。

然而下面的代码:

Pattern p = Pattern.compile(Pattern.quote("Grüsse"), 
                     Pattern.UNICODE_CASE | Pattern.CASE_INSENSITIVE);
System.out.println(p.matcher("Grüße").matches());

产量false。为什么?是否有另一种重现 C# 案例折叠行为的方法?

- - 编辑 - -

正如@VGR 指出的那样,String.toUpperCase将转换ßss,这可能是也可能不是大小写折叠(也许我在这里混淆了概念)。但是,德语语言环境中的其他字符不会“折叠”,例如ü不会变成UE. 因此,为了使我的初始示例更加完整,有没有办法在 Java中使Grüße和比较相等?Gruesse

我在想这个java.text.Normalizer类可以用来做到这一点,但它转换üu?而不是ue. 它也没有提供 a 的选项Locale,这让我更加困惑。

4

3 回答 3

1
于 2021-06-28T09:33:12.477 回答
1

使用 ICU4J 正则表达式,而不是 JDK 的: http ://userguide.icu-project.org/strings/regexp#TOC-Case-Insensitive-Matching

于 2017-01-18T03:03:02.970 回答
0

供参考,以下事实:

  • Character.toUpperCase()不能进行大小写折叠,因为一个字符必须映射到一个字符。

  • String.toUpperCase()将进行案例折叠。

  • String.equalsIgnoreCase()在内部使用Character.toUpperCase() ,因此不进行大小写折叠。

结论(正如@VGR 指出的那样):如果您需要不区分大小写的匹配与大小写折叠,则需要执行以下操作:

foo.toUpperCase().equals(bar.toUpperCase())

并不是:

foo.equalsIgnoreCase(bar)

至于üue平等,我已经设法用RuleBasedCollator我自己的规则来做到这一点(人们希望Locale.German有内置的但唉)。它看起来真的很愚蠢/过度设计,因为我只需要相等,而不是排序/整理,最后我已经解决了一个简单的String.replace比较之前的集合。它很糟糕,但它可以工作并且是透明/可读的。

于 2017-01-18T09:21:42.870 回答