在項目開發中,有時會需要判斷某個程序是否已經運行,一般是通過程序與程序間建立IPC通訊,則能準確的獲取想要的信息。但是如果僅僅只是判斷某程序時否正在運行,專門修改兩個程序的代碼建立進程通信就小題大做了。 一般,操作系統都會記錄每個進程運行信息,我們只需要調用響應的接口,從操作系統拿到這些信息就可以判斷程序是否運行了。
在Windows中,一般調用程序快照API,來獲取某時刻系統正在運行的程序信息,遍歷比較進程名,判斷程序是否正在運行,判斷程序是否運行代碼如下:
bool Widget::isProgramRunning(QString program_name)
{
bool ret = false;
HANDLE info_handle = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); //拍攝系統中所有進程的快照
if(info_handle == INVALID_HANDLE_VALUE)
{
printf("CreateToolhelp32Snapshot fail!!\n\n");
return false;
}
PROCESSENTRY32W program_info;
program_info.dwSize = sizeof(PROCESSENTRY32W); //設置結構體大小
int bResult = Process32FirstW(info_handle, &program_info); //獲取所有進程中第一個進程的信息
if(!bResult)
{
printf("Process32FirstW fail!!\n\n");
return false;
}
while (bResult)
{
char *pro_name = Wchar2char(program_info.szExeFile);
if(program_name == QString(pro_name))
{
ret = true;
break;
}
//獲得下一個進程的進程信息
bResult = Process32Next(info_handle, &program_info);
}
CloseHandle(info_handle);//關閉句柄
return ret;
}
注意API拿到的進程名是寬字節的字符串,需要將其轉換爲單字節字符串再進行程序名稱比較,常用轉換函數如下所示:
char *Widget::Wchar2char(const wchar_t *szStr)
{
int nLen = WideCharToMultiByte( CP_ACP, 0, szStr, -1, NULL, 0, NULL, NULL );
if (nLen == 0)
{
return NULL;
}
char* pResult = new char[nLen];
WideCharToMultiByte( CP_ACP, 0, szStr, -1, pResult, nLen, NULL, NULL );
return pResult;
}
如下爲QT判斷windows中某程序是否在運行的程序示例:
示例代碼下載: https://download.csdn.net/download/fangye945a/12467660
在linux(類unix)中判斷進程是否在運行,通常通過shell命令就能快速判斷,比如(ps | grep usr/bin/wave),如果wave程序正在運行就會有結果輸出,否則無結果輸出。 在C/C++程序中,我們通常利用system()函數調用shell命令,但其只能執行命令而無法獲取執行結果。
若想獲取系統調用命令的執行結果,其實只需使用popen函數即可,其功能類似於system與fopen函數的結合,打開程序後,read其執行結果即可。(注意:調用的命令如果結果返回較慢,需要做延時再進行結果讀取)。
如下爲qnx中判斷某程序是否正在運行的示例函數:
int isWaveRunning()
{
FILE* fp = NULL;
int ret = -1;
char buff[64]={0};
char command[]= "pidin | grep usr/bin/wave"; //linux中命令爲: ps | grep usr/bin/wave
if((fp = popen(command,"r")) == NULL)
{
printf("popen [%s] fail\n\n",command);
return ret;
}
int rc = fread(buff,1,sizeof(buff),fp);
if(rc > 0)
{
printf("----fread: %s\n",buff);
ret = 0;
}
else
{
printf("----fread no data.\n");
}
pclose(fp);
return ret;
}