我正在整理我很久以前编写的一些代码,将它放入方法之类,当我尝试从输入提示输入字符串和LPCWSTR进行目录搜索时。
void GetInfo(string &stdStr, LPCWSTR &wStr)
{
cout << endl << "Enter String: ";
getline(cin, stdStr);
string sTempP = stdStr;
#ifdef UNICODE
std::wstring wTemp = s2ws(stdStr);
wStr = wTemp.c_str();
#else
wStr = stdStr.c_str();
#endif
stdStr = sTempP;
return;
}
当我打电话
string directoryName;
LPCWSTR directory_Name;
GetInfo(directoryName, directory_Name);
std字符串工作正常,但LPCWSTR给了我垃圾。它们都在方法内部工作正常,所以我想知道如何通过引用奇怪地传递这个字符串?
哦,我尝试编写一个函数,将std :: string转换为LPCWSTR并将变量赋值给它,但这也很奇怪。如果在主体中定义,代码工作正常,只有在我遇到问题的函数内部时才会正常工作。
谢谢,
弗雷泽
答案 0 :(得分:3)
我会在该代码中改进一些内容,但您的主要问题是LPCWSTR
是字符串的指针,而不是字符串。您正在为wStr
分配一个新的指针值,但是当您的函数返回时,指向的内存不再有效。
定义UNICODE
时,wTemp
不再在范围内时,该内存不再有效。在未定义UNICODE
的情况下,指针不再有效,因为它指向您调用stdStr
时c_str()
中包含的数据。执行时
stdStr = sTempP;
之前返回给您的指针不再被视为有效。
LPCWSTR
只是typedef
的Windows const wchar_t *
。您最好将GetInfo
的签名更改为以下内容:
void GetInfo(string &stdStr, wstring &wStr);
相应地更改代码。假设您需要派生LPCWSTR
来调用Win32 API函数或其他东西,请按以下步骤操作:
string directoryName;
wstring directory_Name;
GetInfo(directoryName, directory_Name);
LPCWSTR p_directory_Name = directory_Name.c_str();
答案 1 :(得分:0)
LPCWSTR
只是const wchar_t*
的typedef。
您可以使用std::wstring
和std::wstring::c_str()
来检索LPCWSTR
。
此外,如果您愿意,可以使用std::string
的专用外观将std::wstring
转换为boost::lexical_cast
,这是一种非常简单的方法。
答案 2 :(得分:0)
stdStr.c_str()
后stdStr = sTempP
的结果无效。
答案 3 :(得分:0)
LPCWSTR
只是一个指针(在Windows头文件中定义),而std::string
是一个完整的C ++类。
因此,此行只修改输入指针值 - 您需要将值从std::copy
逐字节(stdStr.c_str()
或类似)复制到LPCWSTR
- 已寻址的内存中工作(假设有足够的空间,并纠正空终止)。
wStr = stdStr.c_str();
这也很危险,因为当字符串超出范围时,c_str()
返回的值不再有效,使LPCSWTR
指向内存,这将导致访问时出现未定义的行为。
正如您所看到的,如果您只打算使用已经存在的内存,则通过引用传递原始指针并不是很重要。这只有在您计划将输入指针替换为返回时保持有效的新内存区域的地址时才有用(伴随所有者头痛,所以仍然不是一个好主意)。
答案 4 :(得分:0)
c_str()
方法返回由您调用它们的对象管理的指针。 sTempP
和wTemp
对象是GetInfo
函数的本地对象,因此在函数返回时,这些对象都已被销毁,而{{1}先前返回的指针不好。
看起来c_str()
是为C编程设计的,而不是C ++。因此,您必须找到可以使用的对象类型而不是LPCWSTR
,或者通过分配空间和复制数据并再次取消分配来进行额外的管理。