Как преобразовать std::string
в LPCSTR
? Кроме того, как я могу преобразовать std::string
в LPWSTR
?
Я полностью смущен этими LPCSTR
LPSTR
LPWSTR
и LPCWSTR
.
Являются ли LPWSTR
и LPCWSTR
теми же?
Как преобразовать std::string
в LPCSTR
? Кроме того, как я могу преобразовать std::string
в LPWSTR
?
Я полностью смущен этими LPCSTR
LPSTR
LPWSTR
и LPCWSTR
.
Являются ли LPWSTR
и LPCWSTR
теми же?
str.c_str()
дает вам const char *
, который является LPCSTR
(длинный указатель на константу STRING) - означает, что он является указателем на строку символов 0
. W
означает широкую строку (состоящую из wchar_t
вместо char
).
Вызвать c_str()
, чтобы получить const char *
(LPCSTR
) от std::string
.
Все это в названии:
LPSTR
- (длинный) указатель на строку - char *
LPCSTR
- (длинный) указатель на постоянную строку - const char *
LPWSTR
- (длинный) указатель на строку Unicode (широкая) - wchar_t *
LPCWSTR
- (длинный) указатель на постоянную строку Unicode (широкая) - const wchar_t *
LPTSTR
- (длинный) указатель на TCHAR (Unicode, если UNICODE определен, ANSI if not) string - TCHAR *
LPCTSTR
- (длинный) указатель на постоянную строку TCHAR - const TCHAR *
Вы можете игнорировать L (длинную) часть имен - это сохранение из 16-разрядной Windows.
Это Microsoft typedefs, которые соответствуют:
LPCSTR: указатель на строку с нулевым концом const char
LPSTR: указатель на нулевую завершенную строку char из char
(часто буфер передается и используется как параметр "output" )
LPCWSTR: указатель на строку с нулевым завершением const wchar_t
LPWSTR: указатель на строку с нулевым завершением wchar_t
(часто буфер передается и используется как параметр "output" )
"Преобразовать" a std::string
в LPCSTR зависит от точного контекста, но обычно требуется вызвать .c_str()
.
Это работает.
void TakesString(LPCSTR param);
void f(const std::string& param)
{
TakesString(param.c_str());
}
Обратите внимание, что вы не должны пытаться сделать что-то вроде этого.
LPCSTR GetString()
{
std::string tmp("temporary");
return tmp.c_str();
}
Буфер, возвращаемый .c_str()
, принадлежит экземпляру std::string
и будет действителен только до следующего изменения или уничтожения строки.
Преобразование a std::string
в LPWSTR
является более сложным. Желание LPWSTR
подразумевает, что вам нужен модифицируемый буфер, и вам также нужно быть уверенным, что вы понимаете, какой символ кодирует std::string
. Если std::string
содержит строку, использующую системную по умолчанию кодировку (при условии, что здесь находятся окна), вы можете найти длину требуемого широкого символьного буфера и выполнить транскодирование с помощью MultiByteToWideChar
(функция API Win32).
например.
void f(const std:string& instr)
{
// Assumes std::string is encoded in the current Windows ANSI codepage
int bufferlen = ::MultiByteToWideChar(CP_ACP, 0, instr.c_str(), instr.size(), NULL, 0);
if (bufferlen == 0)
{
// Something went wrong. Perhaps, check GetLastError() and log.
return;
}
// Allocate new LPWSTR - must deallocate it later
LPWSTR widestr = new WCHAR[bufferlen + 1];
::MultiByteToWideChar(CP_ACP, 0, instr.c_str(), instr.size(), widestr, bufferlen);
// Ensure wide string is null terminated
widestr[bufferlen] = 0;
// Do something with widestr
delete[] widestr;
}
Используя LPWSTR
, вы можете изменить содержимое строки, на которую указывает. Используя LPCWSTR
, вы не можете изменить содержимое строки, на которой оно указывает.
std::string s = SOME_STRING;
// get temporary LPSTR (not really safe)
LPSTR pst = &s[0];
// get temporary LPCSTR (pretty safe)
LPCSTR pcstr = s.c_str();
// convert to std::wstring
std::wstring ws;
ws.assign( s.begin(), s.end() );
// get temporary LPWSTR (not really safe)
LPWSTR pwst = &ws[0];
// get temporary LPCWSTR (pretty safe)
LPCWSTR pcwstr = ws.c_str();
LPWSTR
- это просто указатель на исходную строку. Вы не должны возвращать его из функции, используя вышеприведенный пример. Чтобы получить не временный LPWSTR
, вы должны сделать копию исходной строки в куче. Проверьте образец ниже:
LPWSTR ConvertToLPWSTR( const std::string& s )
{
LPWSTR ws = new wchar_t[s.size()+1]; // +1 for zero at the end
copy( s.begin(), s.end(), ws );
ws[s.size()] = 0; // zero at the end
return ws;
}
void f()
{
std::string s = SOME_STRING;
LPWSTR ws = ConvertToLPWSTR( s );
// some actions
delete[] ws; // caller responsible for deletion
}
Ответ MultiByteToWideChar
, который дал Чарльз Бейли, правильный. Поскольку LPCWSTR
- это просто typedef для const WCHAR*
, widestr
в примере кода, его можно использовать везде, где ожидается LPWSTR
или где ожидается LPCWSTR
.
Одна незначительная настройка будет заключаться в использовании std::vector<WCHAR>
вместо управляемого вручную массива:
// using vector, buffer is deallocated when function ends
std::vector<WCHAR> widestr(bufferlen + 1);
::MultiByteToWideChar(CP_ACP, 0, instr.c_str(), instr.size(), &widestr[0], bufferlen);
// Ensure wide string is null terminated
widestr[bufferlen] = 0;
// no need to delete; handled by vector
Кроме того, если вам нужно работать с широкими строками для начала, вы можете использовать std::wstring
вместо std::string
. Если вы хотите работать с типом Windows TCHAR
, вы можете использовать std::basic_string<TCHAR>
. Преобразование из std::wstring
в LPCWSTR
или от std::basic_string<TCHAR>
до LPCTSTR
- это просто вызов c_str
. Это когда вы меняете символы ANSI и UTF-16, которые MultiByteToWideChar
(и его обратный WideCharToMultiByte
) входят в изображение.
Преобразование прост:
std::string myString;
LPCSTR lpMyString = myString.c_str();
Осторожно, что c_str не возвращает копию myString, а просто указатель на строку символов, которая std::string обертывает. Если вам нужна/нужна копия, вам нужно сделать ее самостоятельно, используя strcpy.
Преобразование простое:
std::string str; LPCSTR lpcstr = str.c_str();
Самый простой способ преобразования std::string
в LPWSTR
- на мой взгляд:
std::string
в std::vector<wchar_t>
wchar_t
в векторе. std::vector<wchar_t>
имеет шаблонный ctor, который будет принимать два итератора, такие как итераторы std::string.begin()
и .end()
. Это преобразует каждый char в wchar_t
. Это справедливо только в том случае, если std::string
содержит ASCII или Latin-1, из-за того, что значения Unicode напоминают значения Latin-1. Если он содержит CP1252 или символы из любой другой кодировки, это сложнее. Затем вам нужно будет преобразовать символы.
std::string myString("SomeValue");
LPSTR lpSTR = const_cast<char*>(myString.c_str());
myString - входная строка, а lpSTR - это LPSTR эквивалент.