LoadString是否为其写入的字符串分配内存?

时间:2016-12-21 07:50:18

标签: c++ resources stringreader simplexml-load-string resourcestring

我是c ++的新手,需要一些帮助。 我创建了一个包含字符串的资源专用dll,我需要在另一个项目中使用这个dll来读取存储的字符串。

我编写了以下函数来读取字符串:

LPTSTR GetResourceStr(HMODULE resContainer,int resourceID)
{
    //The stings that are stored in the dll are:
    //
    //ID            |Value|Caption
    //__________________________________________
    //IDS_STRING101 |101  |stringggg
    //IDS_STRING102 |102  |string 102
    //IDS_STRING103 |103  |string 103

    LPTSTR strBuffer = NULL;//is a (non-const) TCHAR string
    if(0!=resContainer){
      int copied=LoadString(resContainer,resourceID ,(LPTSTR)&strBuffer,0); 
    }
    return strBuffer;
}

int _tmain(int argc, _TCHAR* argv[])
{
    HMODULE resContainer=LoadLibraryEx(L"ResourceDll.dll",NULL, LOAD_LIBRARY_AS_DATAFILE);

    LPTSTR msg = GetResourceStr(resContainer,101);
    std::wcout<<msg<<std::endl;
    //Expected output: stringggg
    //The output that i get: stringgggstring 102 string 103
    int i = 0;
    std::cin>>i;
    return 0;
}

我的代码应该更改以获得预期输出 - stringggg ? 为什么会这样? LoadString是否为从资源中读取的字符串分配内存,或者我只是指向内存中已存储字符串的位置? 谢谢你的帮助!!

1 个答案:

答案 0 :(得分:0)

LoadString documentation说:

  

nBufferMax [in]

     

输入:int

     

缓冲区的大小,以字符为单位。如果字符串长于指定的字符数,则该字符串将被截断并以null结尾。如果此参数为0,则lpBuffer将接收指向资源本身的只读指针。

因此,要直接回答您的问题,您只需获取指向存储资源的内存的指针。

但字符串资源不是以空值终止的(有关详细信息,请参阅here),这就是您获得该输出的原因。 LoadString的返回值告诉您单个字符串资源的长度。如果您需要将字符串作为空终止,则必须将字符串复制到单独的缓冲区,如下所示:

WCHAR* pszString;
int iLength = ::LoadString(
    resContainer,
    resourceID,
    reinterpret_cast<LPWSTR>(&pszString),
    0
    );

WCHAR* pszString2 = new WCHAR[iLength + 1];
::StringCchCopyN(pszString2, iLength + 1, pszString, iLength);

或者,您可以使用指向缓冲区的指针(而不是指针指针)作为第3个参数调用LoadString,并将缓冲区的长度作为第4个参数调用,它将字符串资源复制到缓冲区并且null终止它。缺点是如果你没有传递足够大的长度,字符串将被截断,并且无法事先查询资源的长度。