C ++可変長引数を使用するときに、_TCHAR *からchar *に変換するにはどうすればよいですか?
質問
フォーマット_TCHAR *文字列、および複数のchar *文字列を可変長引数を持つ関数に渡す必要があります:
inline void FooBar(const _TCHAR *szFmt, const char *cArgs, ...) {
//...
}
したがって、次のように呼び出すことができます:
char *foo = "foo";
char *bar = "bar";
LogToFileA(_T("Test %s %s"), foo, bar);
明らかに、単純な修正はcharの代わりに_TCHARを使用することですが、残念ながらその贅沢はありません。
文字列をフォーマットできるように、va_startなどでこれを使用する必要があります。
va_list args;
_TCHAR szBuf[BUFFER_MED_SIZE];
va_start(args, cArgs);
_vstprintf_s(szBuf, BUFFER_MED_SIZE, szFmt, args);
va_end(args);
残念ながら、このエラーが発生するため使用できません:
Unhandled exception at 0x6a0d7f4f (msvcr90d.dll) in foobar.exe:
0xC0000005: Access violation reading location 0x2d86fead.
char *を_TCHAR *に変換する必要があると考えていますが、どのようにですか?
解決
%sの代わりに%hsまたは%hSを使用します。これにより、printf()スタイルの関数のAnsiバージョンとUnicodeバージョンの両方で、パラメーターがchar *として解釈されるようになります。つまり、
inline void LogToFile(const _TCHAR *szFmt, ...)
{
va_list args;
TCHAR szBuf[BUFFER_MED_SIZE];
va_start(args, szFmt);
_vstprintf_s(szBuf, BUFFER_MED_SIZE, szFmt, args);
va_end(args);
}
{
char *foo = "foo";
char *bar = "bar";
LogToFile(_T("Test %hs %hs"), foo, bar);
}
他のヒント
通常は次のようになります。
char *foo = "foo";
char *bar = "bar";
#ifdef UNICODE
LogToFileW( L"Test %S %S", foo, bar); // big S
#else
LogToFileA( "Test %s %s", foo, bar);
#endif
あなたの質問は完全に明確ではありません。関数の実装方法と使用方法
ここに私の解決策がありました-改善のための提案を歓迎します!
inline void FooBar(const _TCHAR *szFmt, const char *cArgs, ...) {
va_list args;
_TCHAR szBuf[BUFFER_MED_SIZE];
// Count the number of arguments in the format string.
const _TCHAR *at = _tcschr(szFmt, '%');
int argCount = 0;
while(at) {
argCount++;
at = _tcschr(at + 1, '%');
}
CA2W *ca2wArr[100];
LPWSTR szArgs[100];
va_start(args, cArgs);
for (int i = 1; i < argCount + 1; i++) {
CA2W *ca2w = new CA2W(cArgs);
szArgs[i] = ca2w->m_psz;
ca2wArr[i] = ca2w;
cArgs = va_arg(args, const char *);
}
va_end(args);
// Use the new array we just created (skips over first element).
va_start(args, szArgs[0]);
_vstprintf_s(szBuf, BUFFER_MED_SIZE, szFmt, args);
va_end(args);
// Free up memory used by CA2W objects.
for (int i = 1; i < argCount + 1; i++) {
delete ca2wArr[i];
}
// ... snip ... - code that uses szBuf
}
これは以前にTCHARをcharに変換するために使用したもので、実際に最適化を探していなかったので、それが役立つことを願っています。したがって、最速の方法ではありません。
TCHAR tmp[255];
::GetWindowText(hwnd, tmp, 255);
std::wstring s = tmp;
//convert from wchar to char
const wchar_t* wstr = s.c_str();
size_t wlen = wcslen(wstr) + 1;
char newchar[100];
size_t convertedChars = 0;
wcstombs_s(&convertedChars, newchar, wlen, wstr, _TRUNCATE);
所属していません StackOverflow