gpt4 book ai didi

C++ - 将 wchar_t 转换为网络字节并返回

转载 作者:可可西里 更新时间:2023-11-01 02:33:44 25 4
gpt4 key购买 nike

主要原因是因为我通过套接字发送 Unicode 数据(字节,而不是字符),并且我想确保字节顺序匹配,因为 wchar_t 是 UTF16。

接收程序也是我的另一个,所以我会知道它是 UTF16 并能够做出相应的 react 。

这是我目前使用的算法,但结果很奇怪。 (这是在同一个应用程序中,因为我想在发送之前学习如何转换它)

case WM_CREATE: {   


//Convert String to NetworkByte
wchar_t Data[] = L"This is a string";
char* DataA = (char*)Data;
unsigned short uData = htons((unsigned int)DataA);

//Convert String to HostByte
unsigned short hData = ntohs(uData);
DataA = (char*)&hData;
wchar_t* DataW = (wchar_t*)DataA;
MessageBeep(0);


break;
}

结果:

쳌쳌쳌쳌쳌곭쳌쳌쳌쳌쳌ē쳌쳌쳌쳌This is a string

最佳答案

UTF8 和 UTF16 以完全不同的方式存储文本。将wchar_t* 转换为char* 是没有意义的,这与将float 转换为char* 是一样的。

使用 WideCharToMultiByte 将 UTF16 转换为 UTF8 以发送到网络功能。

当从网络函数接收 UTF8 时,使用 MultiByteToWideChar 转换回 UTF16,以便它可以在 Windows 函数中使用。

例子:

#include <iostream>
#include <string>
#include <windows.h>

std::string get_utf8(const std::wstring &wstr)
{
if (wstr.empty()) return std::string();
int sz = WideCharToMultiByte(CP_UTF8, 0, &wstr[0], -1, 0, 0, 0, 0);
std::string res(sz, 0);
WideCharToMultiByte(CP_UTF8, 0, &wstr[0], -1, &res[0], sz, 0, 0);
return res;
}

std::wstring get_utf16(const std::string &str)
{
if (str.empty()) return std::wstring();
int sz = MultiByteToWideChar(CP_UTF8, 0, &str[0], -1, 0, 0);
std::wstring res(sz, 0);
MultiByteToWideChar(CP_UTF8, 0, &str[0], -1, &res[0], sz);
return res;
}

int main()
{
std::wstring greek = L"ελληνικά";

std::string utf8 = get_utf8(greek);
//use utf8.data() for network function...

//convert utf8 back to utf16 so it can be displayed in Windows:
std::wstring utf16 = get_utf16(utf8);
MessageBoxW(0, utf16.c_str(), 0, 0);

return 0;
}


编辑

另一个显示 UTF16 和 UTF8 之间差异的示例。此示例查看 UTF16 和 UTF8 的字节值。

请注意,对于拉丁字母,UTF8 和 ANSI 字节完全相同。

对于拉丁字母,UTF8 和 UTF16 之间也有相似之处,除了 UTF16 多了一个零。

希腊字母和中文字母有明显的区别。

//(Windows example)
void printbytes_char(const char* ANSI_or_UTF8)
{
const char *bytes = ANSI_or_UTF8;
int len = strlen(bytes);
for (size_t i = 0; i < len; i++)
printf("%02X ", 0xFF & bytes[i]);
printf("\n");
}

void printbytes_wchar_t(const wchar_t* UTF16)
{
//Note, in Windows wchar_t length is 2 bytes
const char *bytes = (const char*)UTF16;
int len = wcslen(UTF16) * 2;
for (size_t i = 0; i < len; i++)
printf("%02X ", 0xFF & bytes[i]);
printf("\n");
}

int main()
{
printbytes_char("ABC");
printbytes_char(u8"ABC");
printbytes_wchar_t(L"ABC");

printbytes_char(u8"ελληνικά");
printbytes_wchar_t(L"ελληνικά");

printbytes_char(u8"汉字/漢字");
printbytes_wchar_t(L"汉字/漢字");
return 0;
}

输出:

"ABC":
41 42 43 //ANSI
41 42 43 //UTF8
41 00 42 00 43 00 //UTF16 (this is little endian, bytes are swapped)

"ελληνικά"
CE B5 CE BB CE BB CE B7 CE BD CE B9 CE BA CE AC //UTF8
B5 03 BB 03 BB 03 B7 03 BD 03 B9 03 BA 03 AC 03 //UTF16

"汉字/漢字"
E6 B1 89 E5 AD 97 2F E6 BC A2 E5 AD 97 //UTF8
49 6C 57 5B 2F 00 22 6F 57 5B //UTF16

关于C++ - 将 wchar_t 转换为网络字节并返回,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40317030/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com