windows编程之多线程总结
来源:互联网 发布:少儿英语教学知乎 编辑:程序博客网 时间:2024/04/30 00:50
用于线程互斥的方法有:原子锁,关键区域(CriticalSection),互斥量(Mutex),。
用于线程同步的方法有:事件(Event),信号量(Semaphore),定时器(这里我们不谈)。
原子锁:
InterlockedIncrement(LONG volatile*Addend);
InterlockedDecrement(LONG volatile*Addend);
InterlockedExchangeAdd(LONG volatile*Addend,LONGValue);
InterlockedExchange(LONG volatile*Target,LONGValue);
例子:
没有使用原子锁的情况:
#include <stdio.h>#include <windows.h>#include <process.h>volatile long g_nLoginCount; unsigned int __stdcall Fun(void *pPM); const DWORD THREAD_NUM = 50;unsigned int __stdcall ThreadFun(void *pPM){g_nLoginCount++;return 0;}int main(){int num= 20;while (num--){g_nLoginCount = 0;int i;HANDLE handle[THREAD_NUM];for (i = 0; i < THREAD_NUM; i++)handle[i] = (HANDLE )_beginthreadex(NULL, 0, ThreadFun, NULL, 0, NULL);WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);for(i=0;i<THREAD_NUM;i++){CloseHandle(handle[i]);}printf("%d个线程执行i++,结果是%d\n", THREAD_NUM, g_nLoginCount);}return 0;}这里解释下为什么搞几个线程,还弄的这么复杂,一个while循环,一个for循环,这是因为不能一次创建很多线程,否则会出问题,你自己可以试试依次性创建100个线程试试,会出问题的。貌似一次最多只能创建64个线程。所以这里采用了这么复杂的方法。
使用原子锁的情况:
unsigned int __stdcall ThreadFun(void *pPM){g_nLoginCount++;InterlockedIncrement(&g_nLoginCount);return 0;}
关键区域(CriticalSection)
一般线程互斥用的多的是这种情况。voidInitializeCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------初始化关键区域
voidDeleteCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------删除关键区域
void EnterCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------进入关键区域
voidLeaveCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------退出关键区域
一般错误的情况:
voidInitializeCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------初始化关键区域
voidDeleteCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------删除关键区域
void EnterCriticalSection(LPCRITICAL_SECTIONlpCriticalSection); -----------进入关键区域#include <stdio.h>#include <process.h>#include <windows.h>long g_nNum;unsigned int __stdcall Fun(void *pPM);const int THREAD_NUM = 10;int main(){HANDLE handle[THREAD_NUM];g_nNum = 0;int i = 0;while (i < THREAD_NUM) {handle[i++] = (HANDLE)_beginthreadex(NULL, 0, Fun, NULL, 0, NULL);}WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);for(i=0;i<sizeof(handle);i++){CloseHandle(handle[i]);}return 0;}unsigned int __stdcall Fun(void *pPM){Sleep(50);g_nNum++;Sleep(0);printf("当前计数为:%d\n",g_nNum);return 0;}
CRITICAL_SECTION g_csThreadCode;InitializeCriticalSection(&g_csThreadCode);DeleteCriticalSection(&g_csThreadCode);
unsigned int __stdcall Fun(void *pPM){Sleep(50);EnterCriticalSection(&g_csThreadCode);g_nNum++;Sleep(0);printf("当前计数为:%d\n",g_nNum);LeaveCriticalSection(&g_csThreadCode);return 0;}
事件(Event)
HANDLECreateEvent(
LPSECURITY_ATTRIBUTESlpEventAttributes,
BOOLbManualReset,
BOOLbInitialState,
LPCTSTRlpName
);---------创建事件。
HANDLEOpenEvent(
DWORDdwDesiredAccess,
BOOLbInheritHandle,
LPCTSTRlpName
);------------打开事件
BOOLSetEvent(HANDLEhEvent);----------触发事件
BOOLResetEvent(HANDLEhEvent);-----------将事件设为未触发
#include <stdio.h>#include <process.h>#include <windows.h>long g_nNum;unsigned int __stdcall Fun(void *pPM);const int THREAD_NUM = 10;CRITICAL_SECTION g_csThreadCode;int main(){InitializeCriticalSection(&g_csThreadCode);HANDLE handle[THREAD_NUM];g_nNum = 0;int i = 0;while (i < THREAD_NUM) {handle[i++] = (HANDLE)_beginthreadex(NULL, 0, Fun, &i, 0, NULL);}WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);for(i=0;i<sizeof(handle);i++){CloseHandle(handle[i]);}DeleteCriticalSection(&g_csThreadCode);return 0;}unsigned int __stdcall Fun(void *pPM){int nThreadNum = *(int *)pPM; Sleep(50);EnterCriticalSection(&g_csThreadCode);g_nNum++;Sleep(0);printf("当前线程为:%d,当前计数为:%d\n",nThreadNum,g_nNum);LeaveCriticalSection(&g_csThreadCode);return 0;}
线程ID不符合要求。。
#include <stdio.h>#include <process.h>#include <windows.h>long g_nNum;unsigned int __stdcall Fun(void *pPM);const int THREAD_NUM = 10;HANDLE g_hThreadEvent;CRITICAL_SECTION g_csThreadCode;int main(){g_hThreadEvent = CreateEvent(NULL, TRUE, FALSE, NULL); InitializeCriticalSection(&g_csThreadCode);HANDLE handle[THREAD_NUM];g_nNum = 0;int i = 0;while (i < THREAD_NUM) {handle[i] = (HANDLE)_beginthreadex(NULL, 0, Fun, &i, 0, NULL);WaitForSingleObject(g_hThreadEvent, INFINITE); ResetEvent(g_hThreadEvent);i++;}WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);for(i=0;i<sizeof(handle);i++){CloseHandle(handle[i]);}CloseHandle(g_hThreadEvent);DeleteCriticalSection(&g_csThreadCode);return 0;}unsigned int __stdcall Fun(void *pPM){int nThreadNum = *(int *)pPM; SetEvent(g_hThreadEvent);Sleep(50);EnterCriticalSection(&g_csThreadCode);g_nNum++;Sleep(0);printf("当前线程为:%d,当前计数为:%d\n",nThreadNum,g_nNum);LeaveCriticalSection(&g_csThreadCode);return 0;}线程ID符合要求。。
互斥量
#include <stdio.h>#include <process.h>#include <windows.h>long g_nNum;unsigned int __stdcall Fun(void *pPM);const int THREAD_NUM = 10;HANDLE g_mutex;int main(){g_mutex = CreateMutex(NULL, FALSE, NULL);HANDLE handle[THREAD_NUM];g_nNum = 0;int i = 0;while (i < THREAD_NUM) {handle[i++] = (HANDLE)_beginthreadex(NULL, 0, Fun, &i, 0, NULL); }WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);CloseHandle(g_mutex);for (i = 0; i < THREAD_NUM; i++)CloseHandle(handle[i]);return 0;}unsigned int __stdcall Fun(void *pPM){Sleep(50);WaitForSingleObject(g_mutex,INFINITE);g_nNum++;Sleep(0);printf("当前计数为:%d\n",g_nNum);ReleaseMutex(g_mutex);return 0;}
信号量(Semaphore)
HANDLECreateSemaphore(
LPSECURITY_ATTRIBUTES lpSemaphoreAttributes,
LONG lInitialCount,
LONG lMaximumCount,
LPCTSTR lpName
);------------------创建信号量
HANDLEOpenSemaphore(
DWORD dwDesiredAccess,
BOOL bInheritHandle,
LPCTSTR lpName
);------------------打开信号量
BOOLReleaseSemaphore(
HANDLE hSemaphore,
LONG lReleaseCount,
LPLONG lpPreviousCount
);--------------------释放信号量
信号量的增:ReleaseSemaphore。信号量的减:WaitForSingleObject(..);当请求信号量时,如果当前信号量为0即不触发状态,那么线程进入阻塞状态,直到信号量值>0,该函数才返回,线程进入可调度状态,同时信号量值减一。
注意:信号量的值不可能小于0。
#include <stdio.h>#include <process.h>#include <windows.h>long g_nNum;unsigned int __stdcall Fun(void *pPM);const int THREAD_NUM = 10;HANDLE g_Semaphore;CRITICAL_SECTION g_CriticalSection;int main(){g_Semaphore = CreateSemaphore(NULL, 0, 1, NULL);InitializeCriticalSection(&g_CriticalSection);HANDLE handle[THREAD_NUM];g_nNum = 0;int i = 0;while (i < THREAD_NUM) {handle[i] = (HANDLE)_beginthreadex(NULL, 0, Fun, &i, 0, NULL);WaitForSingleObject(g_Semaphore, INFINITE);++i;}WaitForMultipleObjects(THREAD_NUM, handle, TRUE, INFINITE);DeleteCriticalSection(&g_CriticalSection);CloseHandle(g_Semaphore);for (i = 0; i < THREAD_NUM; i++)CloseHandle(handle[i]);return 0;}unsigned int __stdcall Fun(void *pPM){int nThreadNum = *(int *)pPM;ReleaseSemaphore(g_Semaphore, 1, NULL);Sleep(50);EnterCriticalSection(&g_CriticalSection);++g_nNum;Sleep(0);printf("当前线程为:%d,当前计数为:%d\n",nThreadNum,g_nNum);LeaveCriticalSection(&g_CriticalSection);return 0;}
- windows编程之多线程总结
- Windows API编程之多线程
- Windows API编程之多线程
- 初识windows编程之多线程
- iOS学习总结之多线程编程(NSThread)
- iOS学习总结之多线程编程(NSThread)-线程的状态
- delphi之多线程编程
- Java之多线程编程
- delphi之多线程编程
- iOS之多线程编程
- IOS编程之多线程
- delphi之多线程编程
- android之多线程编程
- Java之多线程编程
- Android之多线程编程
- Android之多线程编程
- 编程基础之多线程
- python 之多线程编程
- 设置视图圆角,边框宽度/颜色
- OC消息机制(本质的实现方式)
- Linux 进程通信——本地套接字(1)
- java/c++/破解 教学群 群号:145992377
- Mac SVN升级
- windows编程之多线程总结
- cocos2d_环境搭建
- The connection to adb is down, and a severe error has occured. 错误
- linux下vmware安装及问题总结
- oc中消息传递机制-附:对performSelector方法的扩充
- Spring+Quartz实现定时任务的配置方法
- cocos2d_工程结构
- TCP三次握手和time wait
- cocos2d_CCAction