当前位置: C语言 -- 标准库 -- <wchar.h> -- mbrtowc

mbrtowc函数


概要:
#include <wchar.h>
size_t mbrtowc(wchar_t * restrict pwc,
      const char * restrict s,
      size_t n,
      mbstate_t * restrict ps);

描述:

该函数将多字节字符序列转换为宽字符。

如果参数s是空指针,mbrtowc函数等价于

mbrtowc(NULL, "", 1, ps)

这种情况下,参数pwc和参数n的值将被忽略。


如果参数s不是空指针,函数从参数s指向的字节开始最多检查n个字节,以确定构成多字节字符所需的字节数(包括移位序列(shift sequences)。)。如果多字节字符是完整并且有效的,函数将确定对应的宽字符值;如果参数pwc不是空指针,函数将对应宽字符值存入参数pwc指向的对象中。如果对应的宽字符是空宽字符,*ps描述的结果状态将是初始转换状态。


mbtowc函数不同,mbrtowc函数存在一个额外参数ps,参数ps指向对象完整地描述了关联多字节字符序列的当前转换状态。如果参数ps是空指针,函数会使用内部mbstate_t对象,该对象在程序启动时初始化为初始转换状态;这种情况下,mbrtowc函数不要求避免与其它mbrtowc函数调用发生数据竞争。实现应像没有库函数使用ps空指针调用mbrtowc函数一样。mbrtowc函数的返回值不表示编码是否依赖于状态。


参数:
wchar_t * restrict pwc

指向wchar_t类型对象的指针,对应的宽字符将存入该指针指向的对象中。

const char * restrict s

指向多字节字符第一个字节的指针。

size_t n

最多检查的字节数。宏MB_CUR_MAX定义了当前语言环境下多字节字符的最大字节数。

mbstate_t * restrict ps

指向mbstate_t类型对象的指针,指向对象记录关联多字节字符序列的当前转换状态。


返回值:

如果接下来的n个字节或者更少字节构成的多字节字符对应的宽字符是空宽字符,函数返回0

如果接下来的n个字节或者更少字节构成有效的多字节字符,函数返回多字节字符的字节数,其值域区间为[1,n]

如果接下来的n个字节构成不完整的多字节字符(但可能是有效的。),并且所有n个字节都已经被处理(没有值被存储。),函数返回(size_t)(-2)

:当参数n值至少为MB_CUR_MAX时,这种情况只有在参数s指向冗余移位序列(redundant shift sequences)时才会发生(用于依赖状态编码的实现。)。

如果接下来的n个字节或者更少字节不能构成完整且有效的多字节字符(没有值被存储。),将发生编码错误;宏EILSEQ存入errno,并且转换状态是不明确的,函数返回(size_t)(-1)


范例:
1 
2 
3 
4 
5 
6 
7 
8 
9 
10 
11 
12 
13 
14 
15 
16 
17 
18 
19 
20 
21 
22 
23 
24 
25 
26 
27 
28 
29 
30 
31 
32 
33 
34 
35 
36 
37 
38 
39 
40 
41 
42 
43 
44 
/*函数mbrtowc范例*/

#include <locale.h>
#include <stdlib.h>
#include <wchar.h>

int main(void)
{
    setlocale(LC_ALL, "");
    
    static mbstate_t state;
    const char str[] = "中华儿女";
    size_t size = sizeof(str)/sizeof(str[0]);  //存储多字节字符序列的数组的长度。
    const char *ptr = str;
    wchar_t warr[size];  //存储转换后宽字符的数组。
    wchar_t *wptr = warr;
    size_t number;  //mbrtocwc函数的返回值。

    wprintf(L"转换前为%zu个字节的多字节字符序列。\n", size);

    while(number = mbrtowc(wptr, ptr, MB_CUR_MAX, &state))
    {
        if(number == (size_t)(-1))
        {
            wprintf(L"错误序列。\n");
            break;
        }
        else if(number == (size_t)(-2))
        {
            wprintf(L"不完整的多字节字符。\n");
            break;
        }
        else
        {
            ptr += number;
            ++wptr;
        }
    }

    wprintf(L"转换后得到%td个宽字符。\n", (wptr-warr+1));
    
    return 0;
}


输出:

转换前为13个字节的多字节字符序列。

转换后得到5个宽字符。

注:使用ideone.com编译。


相关内容:
mbrlen 确定多字节字符字节数的函数。
wcrtomb 将宽字符转换为多字节字符序列的函数。