线程同步2021"/>
线程同步2021
线程同步
文章目录
- 线程同步
- 一、CriticalSection(关键代码段)
- 二、Mutex(互斥对象)
- 三、Event(事件对象)
- 四、Interlocked(原子锁)
- 五、信号量
- 总结
一、CriticalSection(关键代码段)
只能用于同一个进程中的多线程同步,效率高,速度快。它并不是核心对象,不是属于操作系统维护的,而是属于进程维护的。
CRITICAL_SECTION 结构体
主要函数:
//初始化
void InitializeCriticalSection(LPCRITICAL_SECTION lpCriticalSection);
//进入关键代码段
void EnterCriticalSection(LPCRITICAL_SECTION lpCriticalSection);
//离开关键代码段
void LeaveCriticalSection(LPCRITICAL_SECTION lpCriticalSection);
//销毁关键代码段
void DeleteCriticalSection(LPCRITICAL_SECTION lpCriticalSection);
代码如下(示例):
#include <iostream>
#include <Windows.h>
using namespace std;
CRITICAL_SECTION g_cs; //关键代码段
DWORD WINAPI ThreadFun1(LPVOID lpParameter);
DWORD WINAPI ThreadFun2(LPVOID lpParameter);
int g_resource = 100;int main()
{InitializeCriticalSection(&g_cs); //初始化关键代码段HANDLE hThread1 = CreateThread(0, 0, ThreadFun1, 0, 0, 0);HANDLE hThread2 = CreateThread(0, 0, ThreadFun2, 0, 0, 0);CloseHandle(hThread1);CloseHandle(hThread2);Sleep(1000);return 0;
}DWORD __stdcall ThreadFun1(LPVOID lpParameter)
{while (1){EnterCriticalSection(&g_cs);if (g_resource <= 0){LeaveCriticalSection(&g_cs);break;}else{cout << "ThreadFun1 used :" << g_resource-- << endl;LeaveCriticalSection(&g_cs);Sleep(1); //除了等待之外,还会放弃当前的执行权限}}return 0;
}DWORD __stdcall ThreadFun2(LPVOID lpParameter)
{//同ThreadFun1
}
二、Mutex(互斥对象)
用法同CriticalSection相似,可用于不同进程之间的同步,也可用于防止同一个程序多次运行
Mutex
HANDLE WINAPI CreateMutex(
In_opt LPSECURITY_ATTRIBUTES lpMutexAttributes,
In BOOL bInitialOwner, //创建该对象的线程是否拥有它
In_opt LPCTSTR lpName //互斥对象的名
);
主要函数:
WaitForSingleObject(); //等待一个对象
//打开互斥对象
HANDLE OpenMutex(
DWORD dwDesiredAccess,
BOOL bInheritHandle,
LPCTSTR lpName //名称
);
//结束访问
BOOL ReleaseMutex (HANDLE hMutex);
代码如下(示例):
#include <iostream>
#include <Windows.h>
using namespace std;
HANDLE g_hMutex; //互斥对象
DWORD WINAPI ThreadFun1(LPVOID lpParameter);
DWORD WINAPI ThreadFun2(LPVOID lpParameter);
int g_resource = 100;int main()
{//当前线程拥有对象//g_hMutex = CreateMutex(0, true, 0);//ReleaseMutex(g_hMutex);g_hMutex = CreateMutex(0, false, 0);HANDLE hThread1 = CreateThread(0, 0, ThreadFun1, 0, 0, 0);HANDLE hThread2 = CreateThread(0, 0, ThreadFun2, 0, 0, 0);CloseHandle(hThread1);CloseHandle(hThread2);Sleep(1000);return 0;
}
DWORD __stdcall ThreadFun1(LPVOID lpParameter)
{while (1){WaitForSingleObject(g_hMutex, INFINITE);if (g_resource <= 0){ReleaseMutex(g_hMutex);break;}else{cout << "ThreadFun1 used :" << g_resource-- << endl;ReleaseMutex(g_hMutex);Sleep(1); //除了等待之外,还会放弃当前的执行权限}}return 0;
}
DWORD __stdcall ThreadFun2(LPVOID lpParameter)
{//同ThreadFun1
}
三、Event(事件对象)
HANDLE WINAPI CreateEvent(
In_opt LPSECURITY_ATTRIBUTES lpEventAttributes,
In BOOL bManualReset, //手动重置,还是自动重置 (重置为无信号状态)
In BOOL bInitialState, //初始的信号状态
In_opt LPCTSTR lpName
);
部分函数:
ResetEvent //将事件对象设置为无信号状态
SetEvent //将事件对象设置为有信号状态
WaitForSingleObject(); //等待一个对象
代码如下(示例):
#include <iostream>
#include <Windows.h>
using namespace std;
HANDLE g_hEvent; //互斥事件
DWORD WINAPI ThreadFun1(LPVOID lpParameter);
DWORD WINAPI ThreadFun2(LPVOID lpParameter);
int g_resource = 100;int main()
{// 手动重置,初始无信号g_hEvent = CreateEvent(0, true, false, 0);//设为有信号SetEvent(g_hEvent);HANDLE hThread1 = CreateThread(0, 0, ThreadFun1, 0, 0, 0);HANDLE hThread2 = CreateThread(0, 0, ThreadFun2, 0, 0, 0);CloseHandle(hThread1);CloseHandle(hThread2);Sleep(1000);return 0;
}DWORD __stdcall ThreadFun1(LPVOID lpParameter)
{while (1){WaitForSingleObject(g_hEvent, INFINITE);ResetEvent(g_hEvent);if (g_resource <= 0){SetEvent(g_hEvent);break;}else{cout << "ThreadFun1 used :" << g_resource-- << endl;SetEvent(g_hEvent);Sleep(1); //除了等待之外,还会放弃当前的执行权限}}return 0;
}
DWORD __stdcall ThreadFun2(LPVOID lpParameter)
{//同ThreadFun1
}
四、Interlocked(原子锁)
部分函数:
InterlockedIncrement(); //自加
InterlockedDecrement(); //自减
InterlockedOr(); //或
InterlockedAnd //与
等等…
五、信号量
CreateSemaphore();//创建
ReleaseSemaphore();//释放信号
总结
关于线程同步,异步相关的只是还有待进一步发掘@_@
更多推荐
线程同步2021
发布评论