在VC++ 中编程中,只运行一个实例的方法主要有两类:

1 遍历当前的所有窗口,查找相同的实例。为了便于查找,一般要事先设一个查找标志。

2 利用系统提供的互斥对象或信标,直接让系统抑制重复的实例。

在发现重复运行时,一般还有一个任务,就是激活已经存在的窗口。

一、 第一类方法的实现

下面是一个具体的例子,下图是示例代码运行的情况。

部分关键代码 

1、在App的InitInstance()中枚举所有窗口,查找本程序实例 

 1 HWND oldHWnd = NULL;
 2 
 3 EnumWindows(EnumWndProc,(LPARAM)&oldHWnd);    //枚举所有运行的窗口
 4 
 5 if(oldHWnd != NULL)
 6 
 7 {
 8 
 9 AfxMessageBox("本程序已经在运行了");
10 
11 ::ShowWindow(oldHWnd,SW_SHOWNORMAL);          //激活找到的前一个程序
12 
13 ::SetForegroundWindow(oldHWnd);                //把它设为前景窗口
14 
15 return false;                                  //退出本次运行
16 
17 }

 

2、添加EnumWndProc窗口过程函数://通过自定义的属性名查找同类实例窗口

 1 CString  g_szPropName = "Your Prop Name";   //自己定义一个属性名
 2 
 3 HANDLE   g_hValue = (HANDLE)1;         //自己定义一个属性值
 4 
 5  
 6 
 7 BOOL CALLBACK EnumWndProc(HWND hwnd,LPARAM lParam)
 8 
 9 {
10 
11 HANDLE h = GetProp(hwnd,g_szPropName);
12 
13 if( h == g_hValue)
14 
15 {
16 
17 *(HWND*)lParam = hwnd;
18 
19 return false;
20 
21 }
22 
23 return true;
24 
25 }

 

3、在主窗口的 OnInitDialog()中添加属性 //设置窗口属性

1 SetProp(m_hWnd,g_szPropName,g_hValue);

 

 

2丶第二种方法:

    控制台下:

 1 HANDLE Mutex;
 2 
 3     Mutex = CreateMutex(NULL, TRUE, "me");
 4 
 5      if(GetLastError() == ERROR_ALREADY_EXISTS)
 6 
 7     {
 8 
 9     cout << "only one instance can run!" << endl;
10 
11      return 1;
12 
13     }
14 
15     else
16 
17     {
18 
19        ReleaseMutex(Mutex);
20 
21     }

 

 

 

 MFC下:

 1 BOOL CtestInfoApp::InitInstance()
 2 
 3 {
 4 
 5     HANDLE Mutex;
 6 
 7     Mutex = CreateMutex(NULL, TRUE, "me");
 8 
 9     if(GetLastError() == ERROR_ALREADY_EXISTS)
10 
11     {
12 
13        AfxMessageBox("only one instance can run!");
14 
15        return 0;
16 
17     }
18 
19     else
20 
21     {
22 
23        ReleaseMutex(Mutex);
24 
25     }
26 
27 28 
29 }