此代码:
string a = "abc";
string b = "A?C";
Console.WriteLine("Length a = {0}", a.Length);
Console.WriteLine("Length b = {0}", b.Length);
输出:
Length a = 3
Length b = 4
为什么?我唯一能想到的是中文字符有2个字节长,.Length
方法返回字节计数.
此代码:
string a = "abc";
string b = "A?C";
Console.WriteLine("Length a = {0}", a.Length);
Console.WriteLine("Length b = {0}", b.Length);
输出:
Length a = 3
Length b = 4
为什么?我唯一能想到的是中文字符有2个字节长,.Length
方法返回字节计数.
其他每个人都给出了表面上的答案,但也有更深层次的原因:"字符"的数量是一个难以定义的问题,计算起来可能非常昂贵,而长度属性应该很快.
为什么很难定义?好吧,有几个选项,没有一个比另一个更有效:
代码单元的数量(字节或其他固定大小的数据块;C#和Windows通常使用UTF-16,因此它返回两字节段的数量)肯定是相关的,因为计算机仍需要处理这种形式的数据以用于多种目的(例如,写入文件时关心字节而不是字符)
Unicode代码点的数量非常容易计算(虽然O(n),因为你需要扫描字符串以寻找代理项对),并且可能对文本编辑器很重要....但事实上,这和屏幕上打印的字符数(称为字形)并不是一回事.例如,一些带重音的字母可以用两种形式表示:一个代码点,或者两个成对的点,一个代表字母,另一个说"给我的伙伴字母添加重音".这对角色是两个还是一个?您可以规范化字符串来帮助实现这一点,但并非所有有效字母都有一个单一的代码点表示.
即使是字符的数量也不等于打印字符串的长度,这取决于字体和其他因素,而且由于一些字符在许多字体中打印时有重叠(字距),屏幕上字符串的长度也不一定等于字符长度的总和!
有些Unicode点甚至不是传统意义上的字符,而是某种控制标记.例如字节顺序标记或从右向左指示符.这些算吗?
简而言之,字符串的长度实际上是一个极其复杂的问题,计算它会占用大量的CPU时间和数据表.
此外,这有什么意义?为什么这些指标很重要?好吧,只有你能为你的案子回答这个问题,但就我个人而言,我发现它们通常是无关紧要的.我发现,在逻辑上,限制数据输入是通过字节限制来实现的,因为无论如何,这都是需要传输或存储的.限制显示大小最好由显示端软件完成——如果消息有100个像素,那么适合的字符数取决于字体等,数据层软件无论如何都不知道.最后,考虑到unicode标准的复杂性,如果您try 其他方法,可能会在边缘情况下出现错误.
因此,这是一个很难回答的问题,没有太多的通用用途.代码单元的数量是很容易计算的——它只是底层数据数组的长度——作为一般规则,最有意义/最有用的是一个简单的定义.
这就是为什么b
的长度是4
,超出了表面的解释"因为文档是这么说的".