使用 Qt 将类实例加载到单独的进程中

Posted

技术标签:

【中文标题】使用 Qt 将类实例加载到单独的进程中【英文标题】:Loading class instance into separate process using Qt 【发布时间】:2022-01-07 09:37:03 【问题描述】:

在Python上就可以轻松做到

从多处理导入过程 导入操作系统

def info(title):
    print(title)
    print('module name:', __name__)
    print('parent process:', os.getppid())
    print('process id:', os.getpid())

def f(name):
    info('function f')
    print('hello', name)

if __name__ == '__main__':
    info('main line')
    p = Process(target=f, args=('bob',))
    p.start()
    p.join()

在单独的进程中运行一个简单的函数。我们可以进一步创建在单独进程中加载​​的类的实例:

class FooClass:
    def __init__(self, ...some args...):
        ...

foo = Process(
    target=FooClass,
    args=(...some args for the constructor of Foo...)
)
bar.start()

如果可能的话,我将如何在 Qt 中使用 QProcess 做到这一点?我对这种方法很感兴趣,因为我想在 C++ 以及 PySide/PyQt 中使用它。我知道我可以创建另一个项目,其中生成的二进制文件(仅包含该类及其实例)作为传递给QProcess 实例的命令运行,但这不是我想要的。更不用说,如果我错了,请纠正我,在 Python 情况下,生成的进程会获得父级工作集的“副本”。如果我只是创建另一个应用程序并运行它,显然情况并非如此。

【问题讨论】:

根据我的经验fork()(没有exec())和Qt 的GUI 基础设施并不能相处——即一旦你创建了一个QApplication 对象,分叉进程就不会导致有用的行为;大概是因为 Qt 必须与操作系统的底层窗口管理系统建立连接,并且窗口系统没有设置为处理分叉客户端。所以我认为如果你想在一个单独的 Qt 进程中使用 Qt 对象,你必须“从头开始”spawn() 新进程并让子进程自己创建适当的 Qt 对象。 请注意,生成的子进程可以运行与父进程相同的可执行文件,可能带有一些特殊参数让子进程知道它是子进程和/或父进程想要​​它去做。 【参考方案1】:

Qt 没有用于在不同的进程 中运行函数的标准解决方案。但是有QThread 和QtConcurrent,它们使用线程。

python 拥有多进程模块(而不仅仅是多线程)的主要原因是Global Interpreter Lock (GIL)。但是,当使用 Qt 和 C++ 时,您没有 GIL,因此使用多线程而不是多进程通常会更好。但在某些特殊情况下,您可能希望部分代码在不同的进程中运行,即删除权限。

如果您碰巧在 Linux 下运行,您可能会调查 fork() system call。

【讨论】:

我很清楚QThreadQRunnable 等的存在。我对QProcess 解决方案感兴趣,因为它适用于Qt 的C++ 和Python 绑定。这就是我添加 C++ 标签的原因。我将更新问题以使其更加明显。

以上是关于使用 Qt 将类实例加载到单独的进程中的主要内容,如果未能解决你的问题,请参考以下文章

Qt:如何将类连接到自定义 Qt 设计器小部件

Qt使用QProcess进程间双向通信(linux和win系统)

将 div 加入书签,然后将其加载到单独的 html 文件中

QT程序与 Linux应用程序运 进程间数据通信实例

类加载机制与反射

Java基础 - 静态代码块