【问题标题】:Pass an MFC control to a thread or pass an handle?将 MFC 控件传递给线程或传递句柄?
【发布时间】:2013-01-11 03:40:50
【问题描述】:

我在某处读到过,将 MFC ui 控件作为句柄传递给线程比将指针传递给控件更安全。

选项 1 - 传递指向静态文本的指针:

TestDialog  dlg1;
::_beginthreadex(NULL, 0, &tSetTextByPointer, &dlg1.m_StaticText, 0, NULL);
dlg1.DoModal();

UINT WINAPI tSetTextByPointer(LPVOID arg)
{
    CStatic * pStaticText = static_cast<CStatic*>(arg);
    Sleep(3000);
    pStaticText->SendMessage(WM_SETTEXT, 0, (LPARAM)L"text");

    return 0;
}

选项 2 - 传递句柄:

TestDialog  dlg1;
::_beginthreadex(NULL, 0, &tSetTextByHandle, &(dlg1.m_StaticText.m_hWnd), 0, NULL);
dlg1.DoModal();

UINT WINAPI tSetTextByHandle(LPVOID arg)
{
    HWND * pTextHandle = static_cast<HWND*>(arg);
    Sleep(3000);
    ::SendMessage(*pTextHandle, WM_SETTEXT, 0, (LPARAM)L"text");

    return 0;
}

当通过多个线程访问控件时,我真的应该更喜欢使用句柄吗? 或者在访问控件时依靠 SendMessage() 来解决线程安全问题就足够了吗?

【问题讨论】:

  • 选项 2 并没有真正传递句柄,而是传递了一个指向静态控件句柄成员的指针。因此,一些危险仍然存在。使用句柄的安全性在于它们可以按值传递,而不会从被破坏的对象访问内存。因此,通过 _beginthreadex 将句柄的值作为 static_cast(dlg1.m_StaticText.m_hWnd) 并在您的线程函数中,使用 HWND hwStatic = static_cast(arg) 获取 HWND。
  • @ChristopherOicles - 我认为你是对的,感谢您的评论

标签: c++ multithreading visual-c++ user-interface mfc


【解决方案1】:

首先,您不应该直接从工作线程调用 UI。有很多很好的理由。

但如果您确实需要这个,那么使用原始 HWND 会更安全。否则你应该检查pStaticText-&gt;SendMessage 方法是否是线程安全的。

如果您使用的是 VS2010 及更高版本,我建议您使用这种方法: http://www.terrainformatica.com/2011/01/c0x-running-code-in-gui-thread-from-worker-threads/

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-14
    • 1970-01-01
    • 2023-03-03
    • 1970-01-01
    相关资源
    最近更新 更多