我不确定我的假设是否正确,但我觉得多字节序列的所有四种长度都可以不同,以说明:
说,多字节编码是UTF-8,我们有字符串"\xc3\xb8 \xe2\x86\x82 e\xcc\x88"
,"\u00f8 \u2182 e\u0308"
的UTF-8编码,“øↂë”
此字符串的长度为:
答案 0 :(得分:2)
但有没有一种可移植的方法来确定[字符和光标位置]?
这两者都是模糊概念。例如,罗马10,000是某些字体中的两个光标位置可能取决于特定应用程序选择如何呈现它。
一般来说,人们依赖平台(例如本机文本渲染引擎)或像ICU这样的库来获取光标位置和形状字形等内容。
答案 1 :(得分:2)
Posix接口wcwidth
可用于查找wchar_t
的“光标位置”数。为了获得wchar_t
值(一次一个),您可以使用C99标准库函数mbtowc
,它从字符串中提取单个多字节字符并返回消耗的字节数。 (在字符串上反复调用mbtowc
并每次更新字符串指针将告诉您字符串中存在多少个多字节字符,至少如果多字节编码是UTF-8。)
wcwidth
和mbtowc
的组合可以或多或少地告诉你字符串中有多少个字形(问题#3)。 wcwidth
返回0的wchar_t是零宽度格式控件或组合字符,wcwidth
返回-1的wchar_t是非字符或控制字符(如{{ 1}})。无论哪种方式,都可以忽略,因此字形数实际上是宽度为> 0的wchar_t的计数。
这清楚地表明这四个问题有不同的答案:
字节数。
多字节代码点的数量。
wcwidth大于0的多字节代码点数。
wcwidth大于0的多字节代码点的wcwidth之和。
说了这么多,不能保证\n
返回的值对应于当前控制台字体的实际字符宽度或应用程序使用的Unicode版本。 (我遇到了这两个问题。)wcwidth
返回的值是从当前语言环境中提取的,因此您可以编辑和重新编译语言环境文件以修复错误。例如,请参阅我的答案:How to get ncurses to output astral plane unicode characters