MFC::线程

线程

1.01 创建Worker线程THREAD_PARAM

void CDemoDlg::OnBeginThread() 
{
	m_ThreadParam.hWnd = m_hWnd;
	//启动线程,初始为挂起状态
	AfxBeginThread(ThreadProc, &m_ThreadParam);
}

UINT ThreadProc(LPVOID pParam)
{
	//线程参数
	THREAD_PARAM* pThreadParam = (THREAD_PARAM*)pParam;
	for (int n = 0; n < 10; n++)
	{
		Sleep(100);
		pThreadParam->nData++;
		//向主线程窗口发送消息
		::PostMessage(pThreadParam->hWnd, WM_THREADMSG, 0, 0);
	}
	return 0;
}

1.02 创建UI线程

1、创建一个Dlg
2、创建 CUIThread 继承 CWinThread 类
3、在线程中调用UI
BOOL CUIThread::InitInstance()
{
	//创建并显示一个模式对话框
	CThreadDlg dlg;
	dlg.DoModal();

	//退出线程
	::PostQuitMessage(0);

	return TRUE;
}
void CDemoDlg::OnBeginThread()
{
	//启动线程
	AfxBeginThread(RUNTIME_CLASS(CUIThread));
}

1.03 挂起和恢复线程

void CDemoDlg::OnBeginThread()
{
	if (m_pThread != NULL)
	{
		AfxMessageBox(_T("线程已经启动。"));
		return;
	}
	m_ThreadParam.hWnd = m_hWnd;
	//启动线程,初始为挂起状态
	m_pThread = AfxBeginThread(ThreadProc, &m_ThreadParam, 
		THREAD_PRIORITY_ABOVE_NORMAL, 0, CREATE_SUSPENDED);

	//将线程指针添加到数组中
	m_ThreadArray.Add((CObject*)pThread);

	//线程结束时不自动撤销
	m_pThread->m_bAutoDelete = FALSE;

	//恢复线程运行
	m_pThread->ResumeThread();
}

UINT ThreadProc(LPVOID pParam)
{
	//线程参数
	THREAD_PARAM* pThreadParam = (THREAD_PARAM*)pParam;
	for (int n = 0; n < 100; n++)
	{
		Sleep(100);
		pThreadParam->nData++;
		//向主线程窗口发送消息
		::PostMessage(pThreadParam->hWnd, WM_THREADMSG, 0, 0);
	}
	return 0;
}
void CDemoDlg::OnSuspendThread() 
{
	if (m_pThread != NULL)
	{
		//挂起线程
		m_pThread->SuspendThread();
	}
}

void CDemoDlg::OnResumeThread() 
{
	if (m_pThread != NULL)
	{
		//恢复线程
		m_pThread->ResumeThread();
	}
}
void CDemoDlg::OnEndThread() 
{
	if (m_pThread == NULL)
	{
		AfxMessageBox(_T("线程已经终止。"));
		return;
	}

	m_ThreadParam.bExit = TRUE;

	//等待线程结束
	::WaitForSingleObject(m_pThread->m_hThread, INFINITE);

	delete m_pThread;
	m_pThread = NULL;
}
CDemoDlg::~CDemoDlg()
{
	if (m_pThread != NULL)
	{
		//恢复线程
		m_pThread->ResumeThread();

		//等待线程结束
		::WaitForSingleObject(m_pThread->m_hThread, INFINITE);

		delete m_pThread;
		m_pThread = NULL;
	}
}

1.04 获得线程的退出码

void CDemoDlg::OnBeginThread1() 
{
	if (m_pThread1 != NULL)
	{
		delete m_pThread1;
		m_pThread1 = NULL;
	}

	//启动线程 初始为挂起状态
	m_pThread1 = (CMyThread1*)AfxBeginThread
		(RUNTIME_CLASS(CMyThread1), 
		THREAD_PRIORITY_NORMAL, 
		0, 
		CREATE_SUSPENDED);

	//线程结束时不自动撤销
	m_pThread1->m_bAutoDelete = FALSE;

	//恢复线程运行
	m_pThread1->ResumeThread();	
}

void CDemoDlg::OnGetExitCodeThread1() 
{
	if (m_pThread1 == NULL)
	{
		return;
	}

	DWORD dwExitCode = 0;

	if (::GetExitCodeThread(m_pThread1->m_hThread, &dwExitCode))
	{    
		if (dwExitCode == STILL_ACTIVE)
		{
			AfxMessageBox(_T("线程正在运行\n"));
		}
		else
		{
			CString strText = _T("");
			strText.Format(L"线程退出,退出码:%d\n", dwExitCode);
			AfxMessageBox(strText);
		}
	}
}
void CDemoDlg::OnBeginThread2()
{
	//启动线程 初始为挂起状态
	CWinThread* pThread2 = (CMyThread2*)AfxBeginThread(
		RUNTIME_CLASS(CMyThread2),
		THREAD_PRIORITY_NORMAL,
		0,
		CREATE_SUSPENDED);

	//线程结束时自动撤销(默认)
	pThread2->m_bAutoDelete = TRUE;

	//复制线程句柄
	::DuplicateHandle(GetCurrentProcess(),
		pThread2->m_hThread, 
		GetCurrentProcess(),
		&m_hThread2,
		0,
		FALSE,
		DUPLICATE_SAME_ACCESS);

	//恢复线程运行
  	pThread2->ResumeThread();
}
void CDemoDlg::OnGetExitCodeThread2()
{
	DWORD dwExitCode = 0;
	if (::GetExitCodeThread(m_hThread2, &dwExitCode))
	{    
		if (dwExitCode == STILL_ACTIVE)
		{
			AfxMessageBox(_T("线程正在运行\n"));
		}
		else
		{
			CString strText = _T("");
			strText.Format(L"线程退出,退出码:%d\n", dwExitCode);
			AfxMessageBox(strText);
		}
	}
}

1.05 使用临界区

typedef struct THREAD_PARAM 
{
	HWND hWnd;
	int nData;
	CCriticalSection* pCriticalSection;
}_THREAD_PARAM;

//锁定
pThreadParam->pCriticalSection->Lock();
	todo...
//解锁
pThreadParam->pCriticalSection->Unlock();

1.06 使用互斥量

typedef struct THREAD_PARAM 
{
	HWND hWnd;
	int nData;
	CMutex* pMutex;
}_THREAD_PARAM;

//锁定
SingleLock.Lock();
if (SingleLock.IsLocked())
{
	// todo...
	//解锁
	SingleLock.Unlock();
}
typedef struct THREAD_PARAM 
{
	HWND hWnd;
	int nData;
	CSemaphore* pSemaphore;
}_THREAD_PARAM;

//创建一个信号量,计数的初始值和最大值都为10
m_ThreadParam.pSemaphore = new CSemaphore(10, 10);

//创建SingleLock对象
CSingleLock SingleLock(pThreadParam->pSemaphore);

//锁定
SingleLock.Lock(0);

if (SingleLock.IsLocked())
{
	// todo...
	//解锁
	SingleLock.Unlock();
}

1.06 使用事件

typedef struct THREAD_PARAM 
{
	HWND hWnd;
	int nData;
	CEvent* pExitEvent;
}_THREAD_PARAM;

//创建事件
m_ThreadParam.pExitEvent = new CEvent(FALSE, TRUE);

void CDemoDlg::OnBeginThread()
{
	if (m_pThread != NULL)
	{
		AfxMessageBox(_T("线程已经启动。"));
		return;
	}

	m_ThreadParam.hWnd = m_hWnd;

	//重置事件
	m_ThreadParam.pExitEvent->ResetEvent();

	//启动线程,初始为挂起状态
	m_pThread = AfxBeginThread(ThreadProc, &m_ThreadParam, 
		THREAD_PRIORITY_ABOVE_NORMAL, 0, CREATE_SUSPENDED);

	//线程结束时不自动撤销
	m_pThread->m_bAutoDelete = FALSE;

	//恢复线程运行
	m_pThread->ResumeThread();
}
UINT ThreadProc(LPVOID pParam)
{
	//线程参数
	THREAD_PARAM* pThreadParam = (THREAD_PARAM*)pParam;

	while (TRUE)
	{
		//等待事件
		if (WaitForSingleObject(pThreadParam->pExitEvent->m_hObject, 0)
			== WAIT_OBJECT_0)
		{
			break;
		}

		Sleep(100);

		pThreadParam->nData++;

		//向主线程窗口发送消息
		::PostMessage(pThreadParam->hWnd, WM_THREADMSG, 0, 0);
	}

	return 0;
}
void CDemoDlg::OnEndThread()
{
	if (m_pThread == NULL)
	{
		AfxMessageBox(_T("线程已经终止。"));
		return;
	}

//设置事件
m_ThreadParam.pExitEvent->SetEvent();

//等待线程结束
::WaitForSingleObject(m_pThread->m_hThread, INFINITE);

	delete m_pThread;
	m_pThread = NULL;
}
posted @ 2018-10-23 23:05  osbreak  阅读(230)  评论(0编辑  收藏  举报