使用CString对象getBuffer后一定要进行RealeaseBuffer操作,不然会出现意想不到的错误。
下文转自:http://www.cnblogs.com/zhuyf87/archive/2012/11/02/2751011.html
CSting的GetBuffer()和ReleaseBuffer()
GetBuffer和ReleaseBuffer是从其父类CSimpleStringT继承过来的。GetBuffer的作用是:“Returns a pointer to the internal character buffer”,ReleaseBuffer的作用是:“Releases control of the buffer allocated by GetBuffer.”。这两个函数的常见用法如下:
CString str; const int bufferSize = 10; LPTSTR p = str.GetBuffer(bufferSize); _tcscpy_s(p, bufferSize, _T("abcd1234.")); // use the buffer directly str.ReleaseBuffer(); // Surplus(多余的) memory released, p is now invalid.
给GetBuffer函数传递的参数bufferSize,意思是:“The minimum size of the character buffer in characters. This value does not include space for a null terminator.”。对于调用ReleaseBuffer释放内存时,是否应该带参数,msdn是这样说的:“If you keep track of the string length yourself, you should not append the terminating null character. You must, however, specify the final string length when you release the buffer with ReleaseBuffer. If you do append a terminating null character, you should pass –1 (the default) for the length to ReleaseBuffer, and ReleaseBuffer will perform a strlen on the buffer to determine its length.”。因为ReleaseBuffer函数的默认参数是-1,所以通常在调用ReleaseBuffer函数时省去-1参数的书写。
还有一点非常重要,看如下示例程序:
CString str; const int bufferSize = 10; LPTSTR p = str.GetBuffer(bufferSize); _tcscpy_s(p, bufferSize, _T("abcd")); // use the buffer directly str.Append(_T("1234")); str.ReleaseBuffer(); // Surplus(多余的) memory released, p is now invalid.
当程序执行完Append函数之后,程序员期望的是str字符串里保存的字符序列是abcd1234,但实际上并不是这样。有可能str的内容仍然为abcd,或者直接变为1234。这个问题在我之前的项目中曾经遇到过,最后才把问题定位到这里,来看msdn的注释:“If you use the pointer returned by GetBuffer to change the string contents, you must call ReleaseBuffer before using any other CSimpleStringT member methods.”。也就是说如果程序中通过GetBuffer 函数返回的字符指针修改了字符串的内容,那么必须在使用任何其他的CString类成员函数之前先调用ReleaseBuffer。