2015-07-09 55 views
2

我正在创建一个LPCWSTR的动态数组,并且希望在运行时分配值。 我有以下代码:从std :: wstring Asisgn LPCWSTR数组

cin>>count 
LPCWSTR * lpwcstrArray = new LPCWSTR[count](); 

for (int i = 0; i < count; i++) 
{ 
    // some logic to create different wstring on each iteration 
    wstring tempWString = L"somerandomstuff"; 

    lpwcstrArray[i] = reinterpret_cast<LPSWSTR>tempWString.c_str(); 
} 

现在,如果我访问lpwcstrArray - 所有指数法指向已分配最后一个字符串的数据。

我知道这是不正确的方式来分配值,但我不知道正确的方法。

回答

1

您正在存储的指针指向内部的临时对象std::wstring对象。当这些对象在每次循环迭代中被销毁时,您的数组将留有跳动指针。你需要动态地分配各个串代替,例如:

std::cin >> count 
LPWSTR *lpwstrArray = new LPWSTR[count]; 

for (int i = 0; i < count; i++) 
{ 
    // some logic to create different wstring on each iteration 
    std::wstring tempWString = L"somerandomstuff"; 

    LPWSTR str = new WCHAR[tempWString.length()+1]; 
    const wchar_t *p = tempWString.c_str(); 
    std::copy(p, p+tempWString.length(), str); 

    lpwstrArray[i] = str; 
} 

// use lpwstrArray as needed... 

// don't forget to free the memory when you are done using it... 
for (int i = 0; i < count; i++) 
    delete[] lpwstrArray[i]; 
delete[] lpwstrArray; 

根据你所真正想要实现的东西更像下面会更安全,至少如果你只需要只读访问字符串(你可能做的,为CLPCWSTR代表const,所以阵列的用户不会被修改它们):

std::cin >> count 

std::vector<std::wstring> wstrArray(count); 
for (int i = 0; i < count; i++) 
{ 
    // some logic to create different wstring on each iteration 
    wstrArray[i] = L"somerandomstuff"; 
} 

std::vector<LPWSTR> lpwstrArray(count); 
for (int i = 0; i < count; i++) 
    lpwstrArray[i] = const_cast<wchar_t*>(wstrArray[i].c_str()); 

// use lpwstrArray as needed. if you need to pass it where an 
// LPWSTR* is expected, you can use &lpwstrArray[0] for that... 

// lpwstrArray and wstrArray will be freed automatically 
// when they go out of scope... 
+0

谢谢,我昨天做了第二部分,它工作。谢谢回答。 –

+0

使用第一个循环完成此操作,创建std :: wstring并将其分配给LPCWSTR。 –

3

wstring tempWString在循环的每次迭代中被创建和销毁。
您在lpwcstrArray中有悬挂指针,并且在访问其中一个时出现未定义的行为。
您需要自己分配空间,或者使用std::wstring作为阵列类型而不是LPCWSTR

+0

感谢您的解释,当我不得不使用LPCWSTR *,是什么是在这里分配内存的正确api,我是新的C++ –

+0

你会使用'new'。你可以谷歌它,不要忘记,你必须释放你使用'delete'分配的资源。 –

+0

谢谢,创建一个数组,而不是存储wstring,然后分配,使指针指向有效的内存。 –

-1

尝试的办法

std::wstring ws(_T("Hello")); 
    LPCTSTR lps= (LPCTSTR)(ws.c_str()); 

    TRACE(lps); 

注:

  • 你不应该直接使用在W类型(例如:LPCWSTR)。改用T型(例如:LPCTSTR)。为什么?因为它们会自动翻译成它们应该的版本(对于非Unicode/ASCII的LPCSTR;对于Unicode的LPCWSTR),具体取决于您的项目。

  • 出于同样的原因,你应该围绕你的字符串_T()或在他们之前L

  • 尝试潜入深使用“转到定义”先后开始对LPCTSTR

  • 又见_tcscpy_s函数文档

+0

你的建议是倒退。您应该*避免*使用基于TCHAR的API并改用Unicode API。 Windows已经基于Unicode近二十年了。 TCHAR API用于支持必须支持Windows 9x/ME的应用程序的传统支持。另外,'_T()'(和'TEXT()')与'L“...”'不是一回事。 –

+0

@RemyLebeau我与手中的tchar.h文件。我看到#define _T(x)__T(x)和#define __T(x)L ## x 请解释一下在实际效果方面有什么不同。试图去定义L总是把我带到其他地方,而不是这个L的定义。 – sergiol

+0

没有定义'L',它是作为C/C++语言的一部分内置于编译器本身的。只有当定义了_UNICODE,其中'_T(“x”)'映射到'L“x”'时,'_T()'和'L'才会做同样的事情。当'_UNICODE'没有被定义时,'_T(“x”)'映射到'“x”'。直接将L“x”传递给基于_TCHAR的API是错误的,您必须传递_T(“x”)',以便在两种环境中正确映射。当你必须为Windows的Ansi(Win9x/ME)和Unicode(NT4 +)版本交叉编译单个代码库时,你需要这样做...... –