如何转换 Platform::String 的内容以供需要基于 char* 的字符串的函数使用?我假设 WinRT 为此提供了辅助函数,但我就是找不到它们。
谢谢!
这是一种非常简单的方法,可以在代码中执行此操作,而无需担心缓冲区长度。 仅当您确定正在处理 ASCII 时才使用此解决方案:
Platform::String^ fooRT = "aoeu";
std::wstring fooW(fooRT->Begin());
std::string fooA(fooW.begin(), fooW.end());
const char* charStr = fooA.c_str();
请记住,在此示例中,
char*
位于堆栈上,一旦离开作用域就会消失
Platform::String::Data()
将返回指向字符串内容的 wchar_t const*
(类似于 std::wstring::c_str()
)。 Platform::String
表示不可变字符串,因此没有访问器来获取 wchar_t*
。您需要复制其内容,例如进入 std::wstring
,进行更改。
没有直接的方式来获取
char*
或char const*
,因为Platform::String
使用宽字符(所有Metro风格应用程序都是Unicode应用程序)。您可以使用 WideCharToMultiByte
转换为多字节。
您不应该将宽字符转换为字符,您将损坏每个字符使用多个字节的语言,例如中国人。这是正确的方法。
#include <cvt/wstring>
#include <codecvt>
Platform::String^ fooRT = "foo";
stdext::cvt::wstring_convert<std::codecvt_utf8<wchar_t>> convert;
std::string stringUtf8 = convert.to_bytes(fooRT->Data());
const char* rawCstring = stringUtf8.c_str();
有
String::Data
方法返回 const char16*
,这是原始的 unicode 字符串。
从 unicode 转换为 ascii 或其他任何内容,即
char16*
到 char*
,是另一回事。您可能不需要它,因为现在大多数方法都有其 wchar
版本。
使用wcstombs的解决方案:
Platform::String^ platform_string = p_e->Uri->AbsoluteUri;
const wchar_t* wide_chars = platform_string->Data();
char chars[512];
wcstombs(chars, wide_chars, 512);
解决方案1:
#include <cvt/wstring>
#include <codecvt>
Platform::String^ tTextRT = "TestText";
stdext::cvt::wstring_convert<std::codecvt_utf8<wchar_t>> convert;
std::string stringUtf8 = convert.to_bytes(tTextRT->Data());
const char* rawCstring = stringUtf8.c_str();
但是这个解决方案会产生错误。
错误 C4996 'stdext::cvt':警告 STL4044:stdext::cvt 命名空间的内容是非标准扩展,将来将被删除。可以改用 MultiByteToWideChar() 和 WideCharToMultiByte() 函数。您可以定义 _SILENCE_STDEXT_CVT_DEPRECATION_WARNING 或 _SILENCE_ALL_MS_EXT_DEPRECATION_WARNINGS 来抑制此警告。
解决方案2:
Platform::String^ testText = "Test Text";
std::wstring tTextW(testText->Begin());
std::string tTextA(tTextW.begin(), tTextW.end());
const char* charStr = tTextA.c_str();
但是这个解决方案还有另一个问题:
任何超出 ASCII 字符范围的字符都将被破坏为随机表示,具体取决于执行线程的当前状态。
可行的解决方案:
#include <cvt/wstring>
#include <stringapiset.h>
Platform::String^ testText = "foo";
const wchar_t* pWStr = testText->Data();
int bufferSize = WideCharToMultiByte(CP_UTF8, 0, pWStr, -1, NULL, 0, NULL, NULL);
char* stringUtf8 = new char[bufferSize + 1];
memset(stringUtf8, 0, bufferSize + 1);
if (0 == WideCharToMultiByte(CP_UTF8, 0, pWStr, -1, stringUtf8, bufferSize, NULL, NULL))
{
throw std::exception("Can't convert string to Unicode");
}
const char* rawCstring = std::string(stringUtf8).c_str();
delete[] stringUtf8;