#include <windows.h>
#include <iostream.h>
//1.线程函数声明
DWORD WINAPI Fun1Proc(
LPVOID lpParameter
);
DWORD WINAPI Fun2Proc(
LPVOID lpParameter
);
int tickets=100;
HANDLE g_hEvent; //在3.中,保存事件对象
void main()
{
//2.创建线程
HANDLE hThread1;
HANDLE hThread2;
hThread1=CreateThread(NULL,0,Fun1Proc,NULL,0,NULL);
hThread2=CreateThread(NULL,0,Fun2Proc,NULL,0,NULL);
CloseHandle(hThread1);
CloseHandle(hThread2);
//3.创建事件对象
g_hEvent=CreateEvent(NULL,FALSE/*F为自动重置的事件对象,T是人工重置*/
,FALSE/*非信号状态*/,"SellTicket"/*事件对象的名字 可以使命名的 也可以是匿名NULL的*/);
//命名的事件对象可以用来使同一应用程序 只有一个实例在运行 实现如下
if(g_hEvent)
{
if(ERROR_ALREADY_EXISTS==GetLastError())
{
cout<<"only instance can run!"<<endl;
}
}
SetEvent(g_hEvent);
//设置事件为信号状态,初始化时是非信号状态 (人工重置)
//而线程函数中,一直在等待事件,则保护代码不会被实现
//因为人工重置,存在很多隐患,会导致两个线程同时访问同一资源。
//有两种不同类型的事件对象。一种是人工重置的事件,另一种是自动重置的事件。
//当人工重置的事件得到通知时,等待该事件的所有线程均变为可调度线程。
//当一个自动重置的事件得到通知时,等待该事件的线程中只有一个线程变为可调度线程。
//所以 最好设置成自动重置的事件对象
Sleep(40000);
CloseHandle(g_hEvent);
}
//4.实现线程函数
DWORD WINAPI Fun1Pronc(
LPVOID lpParameter
)
{
while(TRUE)
{
WaitForSingleObject(g_hEvent,INFINITE);
if(tickets>0)
{
Sleep(1);
cout<<"thread1 sell ticket :"<<tickets--<<endl;
}
else
break;
SetEvent(g_hEvent); //设置成有信号状态
}
return 0;
}
DWORD WINAPI Fun1Proc(
LPVOID lpParameter
)
{
while(TRUE)
{
WaitForSingleObject(g_hEvent,INFINITE);
if(tickets>0)
{
Sleep(1);
cout<<"thread1 sell ticket :"<<tickets--<<endl;
}
else
break;
SetEvent(g_hEvent); //设置成有信号状态
}
return 0;
}
DWORD WINAPI Fun2Proc(
LPVOID lpParameter
)
{
while(TRUE)
{
WaitForSingleObject(g_hEvent,INFINITE);
if(tickets>0)
{
Sleep(1);
cout<<"thread2 sell ticket :"<<tickets--<<endl;
}
else
break;
SetEvent(g_hEvent); //设置成有信号状态
}
return 0;
}