使用标准库将 char 转换为 wchar_t?

Convert char to wchar_t using standard library?

我有一个函数需要 wchar_t 数组作为 parameter.I 不知道标准库函数可以将 char 转换为 wchar_t 所以我写了一个快速肮脏的功能,但我想要一个没有错误和未定义行为的可靠解决方案。标准库是否有进行这种转换的函数?

我的代码:

wchar_t *ctow(const char *buf, wchar_t *output)
{
    const char ANSI_arr[]    =  "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789`~!@#$%^&*()-_=+[]{}\|;:'\",<.>/? \t\n\r\f";
    const wchar_t WIDE_arr[] = L"abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789`~!@#$%^&*()-_=+[]{}\|;:'\",<.>/? \t\n\r\f";

    size_t n = 0, len = strlen(ANSI_arr);

    while (*buf) {
        for (size_t x = 0; x < len; x++) {
            if (*buf == ANSI_arr[x]) {
                output[n++] = WIDE_arr[x];
                break;
            }
        }
        buf++;
    }
    output[n] = L'[=11=]';
    return output;
}

这不是从 wchar_tchar 的转换。它是用于销毁 ISO-646 之外的数据的函数。 C 库中的任何方法都不会为您进行这种转换。你可以看看ICU4C库。如果你只在Windows,你可以看看Win32API中的相关函数(WideCharToMultiByte等)

嗯,转换函数在 stdlib.h (*) 中声明。但是你必须知道,对于 latin1 aka ISO-8859-1 字符集中的任何字符,转换为宽字符只是一种分配,因为 unicode 代码低于 256 的字符是 latin1 字符。

因此,如果您的初始字符集是 ISO-8859-1,则转换很简单:

wchar_t *ctow(const char *buf, wchar_t *output) {
 wchar_t cr = output;
    while (*buf) {
        *output++ = *buf++;
    }
    *output = 0;
    return cr;
}

前提是调用者传递了一个指向大小足以存储所有已转换字符的数组的指针。

如果您使用任何其他字符集,则必须使用像 icu 这样的知名库,或者手动构建一个,这对于单字节字符集(ISO-8859-x 系列)来说很简单,对于像 UTF8 这样的多字节的更复杂。

但是不知道你想要处理的字符集,我不能说更多...

顺便说一句,纯 ascii 是 ISO-8859-1 字符集的子集。

(*) 来自 cplusplus.com

int mbtowc (wchar_t* pwc, const char* pmb, size_t max);

Convert multibyte sequence to wide character The multibyte character pointed by pmb is converted to a value of type wchar_t and stored at the location pointed by pwc. The function returns the length in bytes of the multibyte character.

mbtowc has its own internal shift state, which is altered as necessary only by calls to this function. A call to the function with a null pointer as pmb resets the state (and returns whether multibyte characters are state-dependent).

The behavior of this function depends on the LC_CTYPE category of the selected C locale.

在 header wchar.h 中确实如此。它被称为 btowc:

The btowc function returns WEOF if c has the value EOF or if (unsigned char)c does not constitute a valid single-byte character in the initial shift state. Otherwise, it returns the wide character representation of that character.