最近學習了MFC多線程的使用,
寫了一個繼承CWinThread類的類MyThread;
在頭文件開頭用#define定義一個線程函數入口地址(會在下面定義代碼中寫出)
在類的開頭加上IMPLEMENT_DYNCREATE(MyThread, CWinThread)
繼承的子類里面必須重寫兩個函數
一、virtual BOOL InitInstance();
二、virtual int ExitInstance();
聲明一個線程函數,函數名自定,我的類中的線程函數叫StartThread
在聲明完線程函數后再聲明DECLARE_MESSAGE_MAP(),該函數包含了消息映射必要的函數,聲明了它就相當於在類內聲明了這些提供消息映射必要的函數。
頭文件中類定義如下:
#ifndef T_THREAD_H #define T_THREAD_H #pragma once #define WM_TEST WM_USER + 105 //定義線程函數入口地址 class mythread1 : public CWinThread { DECLARE_DYNCREATE(MyThread) public: MyThread(); virtual BOOL InitInstance(); virtual int ExitInstance(); void StartThread(WPARAM wParam, LPARAM lParam); DECLARE_MESSAGE_MAP(); }; #endif
然后在CPP文件開頭加上IMPLEMENT_DYNCREATE(MyThread, CWinThread)
這樣做的意圖在於使能Cobject派生類的對象在運行時動態被創建。
然后在重寫了
BOOL InitInstance();
int ExitInstance();
兩個函數的定義后,在定義線程函數時加上下面的語句
BEGIN_MESSAGE_MAP(MyThread, CWinThread)
ON_THREAD_MESSAGE(WM_TEST, StartThread)
END_MESSAGE_MAP()
這三條代碼的作用是將線程消息傳遞路由定義好
關於這三條語句以及類中聲明的消息映射函數我是參考這篇博客https://blog.csdn.net/luoti784600/article/details/10070939
cpp代碼如下
#include "stdafx.h" #include "t_thread.h" IMPLEMENT_DYNCREATE(MyThread, CWinThread) MyThread::MyThread() { } BOOL MyThread::InitInstance() { return true; } int MyThread::ExitInstance() { return 0; } BEGIN_MESSAGE_MAP(MyThread, CWinThread) ON_THREAD_MESSAGE(WM_TEST, StartThread) END_MESSAGE_MAP() void mythread1::StartThread(WPARAM wParam, LPARAM lParam) { while (true) { TRACE("2\n"); Sleep(1000); } ::AfxEndThread(2015); }
在線程內調用AfxEndThread將會直接結束線程,此時線程的一切資源都會被回收,函數的參數是nExitCode,可以通過GetExitCodeThread獲得。
然后按鍵消息函數中開啟線程,開啟線程的方式是先聲明定義一個線程類指針
MyThread* p_MyThread;
再用AfxBeginThread獲得線程指針
p_MyThread= (MyThread*)AfxBeginThread(RUNTIME_CLASS(MyThread), THREAD_PRIORITY_NORMAL, 0, CREATE_SUSPENDED);
AfxBeginThread有兩種重載函數定義,一種叫工作線程,一種叫用戶界面線程,通過輸入參數的不同區別,本例中使用的是用戶界面線程,
關於AfxBeginThread兩種函數定義的介紹,可以參考https://blog.csdn.net/MissXy_/article/details/80330263。
按鍵消息函數內代碼如下:
void CmythreadDlg::OnBnClickedOk() { // TODO: 在此添加控件通知處理程序代碼 p_MyThread= (MyThread*)AfxBeginThread(RUNTIME_CLASS(MyThread), THREAD_PRIORITY_NORMAL, 0, CREATE_SUSPENDED); p_MyThread->ResumeThread(); p_MyThread->PostThreadMessage(WM_TEST, NULL, NULL); display(); } void CmythreadDlg::display() { while (1) { TRACE("1\n"); Sleep(1000); } }
本例的意圖是用兩個線程,分別打印出1,2兩個數字。
運行結果如下:
記錄完畢,歡迎指出不足!