MFCはUIスレッド||解析できない外部シンボル"public:virtual struct CRuntimeClassを作成
7104 ワード
MFCはUIスレッドとワークスレッドに分かれており、一般的に現在のアプリケーションは1つのメインUIスレッドとNつのワークスレッドで作業を完了している.メインUIスレッドは、ワークスレッドから送信された情報を取得してインタフェースをリフレッシュする.
次の方髪はUIスレッドを使用した方髪です.
1、UIスレッド、CWinThreadクラスを継承する
スレッドInitInstance
次の方髪はUIスレッドを使用した方髪です.
1、UIスレッド、CWinThreadクラスを継承する
1 class CAddDeviceApp : public CWinThread
2 {
3 DECLARE_DYNCREATE(CAddDeviceApp)
4 protected:
5 CAddDeviceApp();
6 public:
7 virtual BOOL InitInstance();
8 virtual int ExitInstance();
9 protected:
10 virtual ~CAddDeviceApp();
11 DECLARE_MESSAGE_MAP()
12
13 };
スレッドInitInstance
1 BOOL CAddDeviceApp::InitInstance()
2 {
3 CSecondThreadDlg dlg;
4 m_pMainWnd = &dlg;
5 INT_PTR nResponse = dlg.DoModal();
6 if (nResponse == IDOK)
7 {
8 }
9 else if (nResponse == IDCANCEL)
10 {
11 }
12 return TRUE;
13 }
m_pMainWnd = &dlg; ,UI , UI DoModal 。
UI :
1 CAddDeviceApp * pThread = (CAddDeviceApp*)AfxBeginThread(RUNTIME_CLASS(CAddDeviceApp));
2、
MFC :MFC ,C Run ,Boost 。1 boost::thread thrd(BoostThreadFunc); 2 3 _beginthread(CRunThreadFunc,0,NULL); // 4 _beginthreadex(NULL, 0, ThreadFunEx, NULL, 0, NULL); 5 pThread=AfxBeginThread(ThreadFunc,NULL,THREAD_PRIORITY_NORMAL);
BOOSTスレッドの作成方法は種類が多く、関数オブジェクト、Boost::bindメンバー関数など多様な方法で作成できますが、仕事があまり時間がないのでまとめません.
一般的にMFCはAfxBeginThreadの方が安全です.
*******************************************************************************************************************************************************************************************
解析できない外部シンボル「public:virtual struct CRuntimeClass*_thiscall CAddDeviceApp::GetRuntimeClass(void)const」が表示された場合
などのエラー:
以下の原因は上述の誤りを引き起こす:1,にある.hファイルにDECLARE_と書いてありますDYNAMICは、cppファイルにIMPLEMENTと書かれていませんDYNAMIC 2,はい.hファイルにDECLARE_と書いてありますDYNCREATEですが、cppファイルにIMPLEMENTと書かれていませんDYNCREATE
カスタムクラスを作成するときは、クラス定義にDECLARE_が含まれている場合に知っておく必要があります.DYNAMIC、クラス宣言にIMPLEMENTを含める必要があります.DYNAMIC;クラス定義にDECLARE_が含まれている場合DYNCREATE、クラス宣言にIMPLEMENTを含める必要があります.DYNCREATE
.hクラスで定義
DECLARE_DYNCREATE(CMyWinThread)
DECLARE_MESSAGE_MAP()
.cppクラスで定義
IMPLEMENT_DYNAMIC(CMyWinThread,CWinThread) BEGIN_MESSAGE_MAP(CMyWinThread, CWinThread) END_MESSAGE_MAP()
メッセージがマッピングされていることを覚えておいてください.hファイルと.cppファイルには一つ一つ対応しています.
****************************************************************
実行中にメモリ不足が発生した場合:
スレッドを作成するコードを次のように変更します.
CAddDeviceApp * pThread=NULL; pThread= new CAddDeviceApp(); pThread->CreateThread();
CAddDeviceAppクラスの定義:
class CAddDeviceApp : public CWinThread { DECLARE_DYNCREATE(CAddDeviceApp) public: CAddDeviceApp(); public: virtual BOOL InitInstance(); virtual int ExitInstance();//void ShowNormalMsg(LPCTSTR lpszText); public: virtual ~CAddDeviceApp(); DECLARE_MESSAGE_MAP() };
実装方法:
CAddDeviceApp::CAddDeviceApp() { } CAddDeviceApp::~CAddDeviceApp() { } IMPLEMENT_DYNAMIC(CAddDeviceApp,CWinThread) BEGIN_MESSAGE_MAP(CAddDeviceApp, CWinThread) END_MESSAGE_MAP()BOOL CAddDeviceApp::InitInstance(){INT_PTR nRes;CNewDiaDlg stat_T;//モードダイアログのクラスm_pMainWnd=&stat_T;nRes=stat_T.DoModal();if(IDD_DIALOG 1==nRes)return TRUE;}int CAddDeviceApp::ExitInstance() {return CWinThread::ExitInstance(); }
終了スレッドモードダイアログボックスを閉じる方法:
HWND hPopuphWnd =::GetForegroundWindow();//現在実行中のウィンドウのハンドルを取得する::PostMessage(hPopuphWnd,WM_CLOSE,0,0);注:現在実行中のウィンドウとしてスレッドがポップアップされたモードダイアログボックスを使用します.正しく閉じるには、まずモードダイアログボックスを閉じる必要があります.
メインスレッドのウィンドウを再実行します.