如何判断程序是否重复运行的几种方法
来源:互联网 发布:男士护肤推荐 知乎 编辑:程序博客网 时间:2024/06/07 10:54
如何判断程序是否重复运行的几种方法
版权声明:本文为博主原创文章,未经博主允许不得转载。
如何判断程序是否重复运行的几种方法
判断程序的实例是否已经启动,无非是通过设立某个标识,让下次启动程序时知道该实例已经运行。嗯,可是在WIN32中每个进程都有自已独立的空间,那么如何处理呢,下面提供两种方案:
方案一,使用内核对象
因为内核对象是可以跨进程存在的,因此我们可以通过创建一个命名互斥体(Mutex)内核对象来判断,当用同一个名字的来创建Mutex时,CreateMutex会返回一个指向该互斥体的句柄,但是GetLastError会得到ERROR_ALREADY_EXISTS的返值。因此我们就可以判断程序已有一个实例在运行。下面是其中的关键代码
m_hmutex = ::CreateMutex( NULL,FALSE,appID);
if(m_hmutex == NULL)return FALSE; //
if( ::GetLastError() == ERROR_ALREADY_EXISTS )//
{
return FALSE;
}
else
{
return TRUE;
}
方案二,使用共享数据段
背景知识:EXE和DLL文件映像由许多区组成如代码在.text段中,初始化数据在.data段中,未初始化数据在.bss段中。系统在加载EXE和DLL时,实际上是使用了内存映射,为了减少加载时间,同一EXE文件多个实例实际在系统中只有一份。但一般地如果其中某个实例对某个数据区进行写时,系统会使用Copy-On-Write机制将这个数据区在虚拟内存中复制一份出来,并映射到该实例原先的地址空间,也就实现了进程数据的唯一性,而不会干扰其它进程。但是我们可以通过设置让系统关闭掉这个机制。哪么如何做呢?
在Visual Studio中你可以程序中加上以下几行:
#pragmacomment(linker,"/SECTION:Share,RWS") //指示编译器Share是可读写和共享的,当然你也可以通过设置链接器选项直接加上 /SECTION:Share,RWS,不过我更喜欢这个,因此其他朋友就不必自已去设置这个选项了。
#pragmadata_seg("Share") //开始自已的数据段
int g_AppInit =0; //必需初始化,否则不会将编译器不会将其放入Share这个区
#pragmadata_seg()
还有一种将某个变量置于特别数据段的方式
__declspec(allocate("Share"))int g_AppInit =0;
这种方式的好处是无论你初不初始化这个变量都将置于该Share段内
哪么如何判断呢是否启动了实例呢,很简单,看以下代码
g_AppInit ++ ;
if(g_AppInit >1)
{
AfxMessageBox("A instance are runed!");
return FALSE;
}
相关的问题:如何通知前一个实例
解决了重复启动的问题,为了获得更佳的用户体验,往往我们要使前一个实例激活,如何做呢?使用消息是一个不错的方法。首先你需要在启动程序时登记一个全局消息。
WM_APPACTIVE = ::RegisterWindowMessage(appID);
相同的appID字符串会给出相同的消息值,并且总是在0xC000- 0xFFFF区间中,然后当你发现已启动程序实例时通知前一个实例:
DWORD dectype = BSM_APPLICATIONS; //仅向应用程序发送
BroadcastSystemMessage(BSF_POSTMESSAGE,
&dectype,
WM_APPACTIVE,
0,0);
前一个程序实例收到这个消息后,进行处理,可以前置窗口激活等等。- 如何判断程序是否重复运行的几种方法
- 如何判断程序是否重复运行的几种方法
- 如何判断程序是否重复运行的几种方法
- 如何判断程序是否重复运行的几种方法
- 防止C++程序重复运行的几种方法
- 防止C++程序重复运行的几种方法
- 防止C++程序重复运行的几种方法
- 判断程序实例是否已经运行的N种方法
- 判断程序实例是否已经运行的N种方法
- 判断程序实例是否已经运行的N种方法
- jquery判断是否的几种方法
- 如何判断程序是否第一次运行
- 如何判断程序是否第一次运行
- android判断程序是否运行的代码
- jQuery 判断 checkbox 是否被选中的几种方法
- C# 判断是否为数字的几种方法
- VC 判断文件是否存在的几种方法
- jQuery 判断 checkbox 是否被选中的几种方法
- C++根据扩展名获取文件图标、类型
- Android中使用aidl在进程间通信(IPC)
- 数据结构总结---树
- android-----View工作原理系列(一)
- 设计模式--spring源码中使用策略模式(Strategy Pattern)
- 如何判断程序是否重复运行的几种方法
- BCE0004: Ambiguous reference 'preview': CameraMotionBlurEditor.preview, UnityEditor.Editor.preview.
- 成员变量、类变量、局部变量的区别
- 原生下拉刷新SwipeRefreshLayout的使用
- win7 安装ubuntu14.04 双系统 加hisi3531 交叉编译移植
- 剑指offer-3-面试14:调整数组顺序使奇数位于偶数前面
- UIButton和UILabel的宽与高
- 计算给定时间与现在的时间差
- MyEclipse 快捷键