.net NET的String.normalize做什么?

0yycz8jy  于 2022-12-14  发布在  .NET
关注(0)|答案(4)|浏览(122)

MSDN article on String.Normalize简单地说:
返回一个新字符串,其二进制表示形式为特定的Unicode范式。
有时也指“Unicode范式C”。
我只是想知道,这是什么意思?这个功能在真实的生活中有什么用?

yrdbyhpb

yrdbyhpb1#

格式C和格式D之间的一个区别是如何表示带重音的字母:表单C使用单个带重音字母的代码点,而表单D将其分成字母和重音。
例如,“à”可以是代码点224(“拉丁小写字母A带抑音符”),也可以是代码点97(“拉丁小写字母A”)后跟代码点786(“组合抑音符”)。逐个字符比较会发现它们是不同的。
一个副作用是,这使得创建“删除重音符号”方法变得容易。

public static string RemoveAccents(string input)
{
    return new string(input
        .Normalize(System.Text.NormalizationForm.FormD)
        .ToCharArray()
        .Where(c => CharUnicodeInfo.GetUnicodeCategory(c) != UnicodeCategory.NonSpacingMark)
        .ToArray());
    // the normalization to FormD splits accented letters in letters+accents
    // the rest removes those accents (and other non-spacing characters)
    // and creates a new string from the remaining chars
}

或者让“高度安全”的ROT13编码与重音一起工作:

string Rot13(string input)
{
    var v = input.Normalize(NormalizationForm.FormD)
        .Select(c => {
            if ((c>='a' && c<='m') || (c>='A' && c<='M'))
                return (char)(c+13);
            if ((c>='n' && c<='z') || (c>='N' && c<='Z'))
                return (char)(c-13);
            return c;
        });
    return new String(v.ToArray()).Normalize(NormalizationForm.FormC);
}

这将把“Crème brälée”转换为“Per zr oeyr”(当然反之亦然),首先将“character with accent”代码点拆分为单独的“character”和“accent”代码点(FormD),然后只对字母执行ROT13转换,然后尝试重新组合它们(FormC)。

2skhul33

2skhul332#

它确保可以比较unicode字符串是否相等(即使它们使用不同的unicode编码)。
摘自Unicode标准附录#15:
基本上,Unicode规范化算法将所有组合标记按指定顺序放置,并使用分解和组合规则将每个字符串转换为Unicode规范化形式之一。然后,对转换后的字符串进行二进制比较,以确定是否等效。

c6ubokkw

c6ubokkw3#

在Unicode中,(组合)字符可以具有唯一的代码点,也可以具有由基本字符及其重音组成的代码点序列。
Wikipedia列出越南语(U+1EBF)及其分解序列U+0065(e)U+0302(抑扬重音)U+0301(锐重音)作为例子。
string.normalize()在4种范式之间转换一个可以用Unicode编码的字符串。

8cdiaqws

8cdiaqws4#

这个链接有一个很好的解释:
http://unicode.org/reports/tr15/#Norm_Forms
据我推测,这样您就可以比较两个unicode字符串是否相等。

相关问题