2012-07-24 109 views
2

这就是问题所在: 我不喜欢我的程序的多个实例,这就是我禁用它们的原因。我的程序打开一个特定的MIME类型。在我的系统(Ubuntu的12.04),当我双击其中的一个文件,就执行:如何同时处理多个并发实例?

/usr/bin/myprogram /path/to/double/clicked/file.myextension 

正如我所说的,我不喜欢多个实例,因此,如果该程序已经运行和用户选择打开其中一个文件,DBus消息正在发送到已经存在的实例,以便照顾打开的文件。所以,如果有一个已经运行的实例,用户可从中选择3个文件和我的程序打开并击中[确定]按钮,系统执行:

/usr/bin/myprogram /path/to/double/clicked/file1.myextension 
/usr/bin/myprogram /path/to/double/clicked/file2.myextension 
/usr/bin/myprogram /path/to/double/clicked/file3.myextension 

所有这些实例的检测已经运行的实例,并发送打开文件。根本没有问题,直到现在。

但是,如果没有已经运行的实例并且用户选择用我的程序完全打开3个文件会怎么样?再次,系统将同时调用,:

/usr/bin/myprogram /path/to/double/clicked/file1.myextension 
/usr/bin/myprogram /path/to/double/clicked/file2.myextension 
/usr/bin/myprogram /path/to/double/clicked/file3.myextension 

和所有这些情况都将认识到,有一个已经运行的情况下,它会试图发送一个消息的DBus到已运行的情况下,它会退出。所以,所有这3个进程都会做同样的事情,没有任何东西会运行。

我该如何避免这个问题?

PS:

bool already_runs(){ 
return !system("pidof myprogram | grep \" \" > /dev/null"); 
} 
+0

打开多个文件时,是否应该将所有三条路径都传递给一个命令?例如。/usr/bin/myprogram file1 file2 file3 – Alan 2012-07-24 14:16:58

+0

@Alan:无论是否存在,至少仍然有人可能通过其他方式快速连续运行该程序三次:-)需要的是方式之一的程序副本宣布自己是“第一个”。例如,这可能是通过获取特定文件的锁,但我不知道QT,如果QT提供了一些帮助机制,这将是一个垃圾回答。 – 2012-07-24 14:26:11

+0

您不仅需要检测另一个实例正在运行,而且还有一个正在运行的实例已经接受它是一个实例。 – bames53 2012-07-24 14:42:14

回答

0

我会使用一些共享内存来存储第一进程的PID:为了我执行下面的代码来检测是否有已在运行的实例。 QSharedMemory班将帮助你在这里。

您的程序应该做的第一件事就是尝试创建一个共享内存段(使用您自己编写的密钥)并将其存储在其中。如果创建调用失败,则可以尝试附加到段。如果成功,那么你可以从它读取原始进程的PID。

编辑:另外,remomber在写入或读取共享内存之前使用lock(),然后在完成时调用unlock()。

+0

链接不'这里是[QSharedMemory的Qt 4.8参考](http://doc.qt.io/qt-4.8/qsharedmemory.html)和[QtredMemory的Qt 5.5参考](http://doc.qt。 IO/QT-5/qsharedmemory.html)。 – basic6 2015-10-24 21:53:15

0

在DBus中执行此操作的标准方法是在总线上获取应用程序的名称;一个实例将赢得比赛并且可以成为正在运行的实例。然而,你应该能够使用Qt功能来完成这项工作,它将与你的其他应用程序更好地集成在一起;见Qt: Best practice for a single instance app protection

相关问题