我已经使用英语和希腊语字符定义了相同的char数组。
char myText[]="ΗΤΙΑ ΗΤΙΑΑΑ ΛΟΥΛΟΥΔΙΑΣΜΕΝΗ!!!1234567890";
// char myText[]="HTIA HTIAAA LOULOUDIASMENH!!!1234567890";
当我使用char数组的strlen(myText);
打印长度时,第一个具有希腊语UTF8字符的长度为63个字符但第二个具有39.为什么会发生这种情况?我可以解决这个问题,或者正确的问题是如何使用希腊语Unicode希腊字符语法,以便程序正确理解它们?
我将char数组发送到led矩阵,并且当字符为英语时,i消息不会显示在屏幕上。似乎希腊字符或非ASCII字符大于一个字节。
我有一个switch函数,用于检查字符并为每个字母返回一个合适的字节数组。我已将开关的默认情况设置为字符!
因此,我获得HTIA HTIA
而不是获得!H!T!I!A!
。所以我的开关将希腊字符理解为超过1个字节,并首先返回默认情况,即!
,然后返回正确的字符。
此外,当我尝试打印文本时,我在串行监视器上出现错误(字符无法正确显示)。
答案 0 :(得分:1)
由于UTF-8字符可以有多个字节,并且strlen只计算直到第一个空字符的字节数,因此strlen将超过UTF-8字符串的长度。一种解决方案是使用mbstowcs()将字符串转换为宽字符串,然后使用wcslen()来获取宽字符串的长度。
P.S。 Here展示了问题中提到的效果。
答案 1 :(得分:0)
UTF-8是一种可变长度编码,因此有些字符只占用一个字节,而其他字符占用几个字符。
如果使用switch
语句逐个字符地处理字符串,那么您应该使用宽字符字符串:
#include <stddef.h>
wchar_t myText[]= L"ΗΤΙΑ ΗΤΙΑΑΑ ΛΟΥΛΟΥΔΙΑΣΜΕΝΗ!!!1234567890";
宽字符的类型为wchar_t
而不是char
,并且其大小足以存储当前语言环境中的任何单个字符。宽字符串常量以L
字符为前缀。
在switch
语句中,您可以在案例表达式中使用宽字符常量(也以L
字符为前缀):
switch (c)
{
case L'Λ':
/* handle capital lambda */
break;
case L'Α':
/* handle capital A */
break;
/* ... */
}