在MFC中设置UI标题时出错

error in set UI title in MFC

本文关键字:标题 出错 UI 设置 MFC      更新时间:2023-10-16

我试图改变一个MFC窗口的标题如下:

BOOL CameraUI::OnInitDialog()
{
    // set ui title 
    TCHAR wintitle[100];
    _stprintf_s(wintitle, sizeof wintitle, _T("Camera %u"), (UINT) getSerialNumber());  
    SetWindowText(wintitle);
return TRUE;
}

当我调试时,我在函数末尾得到这个错误:

Run-Time Check Failure #2 - Stack around the variable 'wintitle' was corrupted.

我正在使用MSVC 2008。我做错了什么?!

请勿按原样使用sizeof winTitle

_stprintf_s函数需要的是characters的个数,而不是bytes的个数。

http://msdn.microsoft.com/en-us/library/ce3zzk1k.aspx

由于显然您使用的是TCHAR,那么字符数如下:

sizeof(winTitle) / sizeof(winTitle[0])

sizeof(winTitle) / sizeof(TCHAR)

在MS世界中,TCHAR要么是1字节(如果构建是MBCS),要么是2字节(这是Unicode)。

假设您正在使用Unicode,通过仅声明sizeof winTitle,您指定您的数组可以容纳最多200个字符,但事实并非如此(显示sizeof winTitle给出的内容,您将看到它是200)。

使用std::stringstd::ostringstream代替字符缓冲区和sprintf。通过这种方式,您可以通过让这些类为您管理内存来避免缓冲区溢出。你唯一需要直接与c风格字符串交互的时候是在与Win32函数交互的时候。

std::ostringstream output;
std::string wintitle;
output << "Camera " << (UINT) getSerialNumber();
wintitle = output.str();
SetWindowText(wintitle.c_str());
return TRUE;

_stprintf_s有一个模板化的重载,它不需要缓冲区大小参数。您可以将错误行写成

_stprintf_s(wintitle, _T("Camera %u"), (UINT) getSerialNumber());

模板将自动推断出目标缓冲区的正确长度,并保护您避免传递错误的缓冲区大小。