如何比较C中的多字节字符

前端之家收集整理的这篇文章主要介绍了如何比较C中的多字节字符前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我尝试解析文本并在其中找到一些字符.我使用下面的代码.它适用于普通字符,如abcdef,但它不适用于öçşğüı. GCC提供编译警告.我该怎么做才能与öçşğüı合作?

代码

#include <stdio.h>
#include <ctype.h>
#include <string.h>

int main()
{
    char * text = "öçşğü";
    int i=0;

    text = strdup(text);

    while (text[i])
    {       
        if(text[i] == 'ö')
        {
            printf("ö \n");
        }

        i++;
    }

    return 0;
}

警告 :

warning: multi-character character constant [-Wmultichar]
warning: comparison is always false due to limited range of data type [-Wtype-limits]

在while循环中打印char的地址时有10个地址

printf("%d : %p \n",i,text[i]);

输出

0 : 0xffffffc3 
1 : 0xffffffb6 
2 : 0xffffffc3 
3 : 0xffffffa7 
4 : 0xffffffc5 
5 : 0xffffff9f 
6 : 0xffffffc4 
7 : 0xffffff9f 
8 : 0xffffffc3 
9 : 0xffffffbc

而strlen是10.

但是如果我使用abcde:

0 : 0x61 
1 : 0x62 
2 : 0x63 
3 : 0x64 
4 : 0x65

而strlen是5.

如果我使用wchar_t进行文本输出

0 : 0xa7c3b6c3 
1 : 0x9fc49fc5 
2 : 0xbcc3

而strlen是10,wcslen是3.

解决方法

要浏览字符串中的每个字符,可以使用mblen.您还需要设置正确的语言环境(多字节字符串表示的编码),以便mblen可以正确解析多字节字符串.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <locale.h>

int main()
{
    char * text = "öçşğü";
    int i=0,char_len;

    setlocale(LC_CTYPE,"en_US.utf8");

    while ((char_len = mblen(&text[i],MB_CUR_MAX)) > 0)
    {
        /* &text[i] contains multibyte character of length char_len */
        if(memcmp(&text[i],"ö",char_len) == 0)
        {
            printf("ö \n");
        }

        i += char_len;
    }

    return 0;
}

有两种类型的字符串表示,使用多字节(8位字节)或宽字节(大小取决于平台).多字节表示具有可以使用char *(在代码中通常使用c字符串)表示的优点,但缺点是多个字节表示字符.宽字符串使用wchar_t *表示. wchar_t的优点是一个wchar_t是一个字符(但正如@anatolyg所指出的,在wchar_t无法表示所有可能的字符的平台上,这个假设仍然可能出错).

您是否使用十六进制编辑器查看了源代码?字符串“öçşğü”实际上由存储器中的多字节字符串c3 b6 c3 a7 c5 9f c4 9f c3 bc(UTF-8编码)表示,当然具有零终止.您只看到5个字符,因为您的UTF-8感知查看器/浏览器正确呈现了字符串.很容易意识到strlen(text)为此返回10,而上面的代码只循环5次.

如果使用宽字节字符串,可以按照@WillBriggs的说明完成.

原文链接:https://www.f2er.com/c/118462.html

猜你在找的C&C++相关文章