4

我想在应用程序的其余部分继续运行时生成另一个进程以异步显示错误消息。

我正在使用multiprocessingPython 2.6 中的模块来创建进程,并尝试使用TKinter.

此代码在 Windows 上运行良好,但在 Linux 上运行它,TKinter如果我调用'showerror("MyApp Error", "Something bad happened.")'. 如果我通过直接调用在同一进程中运行它,它确实showerrorprocess会出现。鉴于此,它似乎TKinter工作正常。我可以打印到控制台并从 生成的进程中执行其他操作multiprocessing,因此它似乎也可以正常工作。

他们只是似乎没有一起工作。我需要做一些特别的事情来允许衍生的子进程创建窗口吗?

from multiprocessing import Process
from Tkinter import Tk, Text, END, BOTH, DISABLED
import sys
import traceback

def showerrorprocess(title,text):
    """Pop up a window with the given title and text. The
       text will be selectable (so you can copy it to the
       clipboard) but not editable. Returns when the
       window is closed."""
    root = Tk()
    root.title(title)
    text_box = Text(root,width=80,height=15)
    text_box.pack(fill=BOTH)
    text_box.insert(END,text)
    text_box.config(state=DISABLED)
    def quit():
        root.destroy()
        root.quit()
    root.protocol("WM_DELETE_WINDOW", quit)
    root.mainloop()

def showerror(title,text):
    """Pop up a window with the given title and text. The
       text will be selectable (so you can copy it to the
       clipboard) but not editable. Runs asynchronously in
       a new child process."""
    process = Process(target=showerrorprocess,args=(title,text))
    process.start()

编辑

问题似乎TKinter是由父进程导入,并“继承”到子进程中,但不知何故,它的状态与父进程密不可分,无法在子进程中工作。只要您确保TKinter在生成子进程之前不导入,它就会起作用,因为这是第一次导入它的子进程。

4

2 回答 2

4

这个讨论可能会有所帮助。

这是我发现的一些示例问题:

  1. 虽然多处理模块密切关注线程,但它绝对不是完全匹配的。一个例子:因为一个进程的参数必须是pickleable,我不得不经历很多代码更改以避免传递Tkinter对象,因为这些是不可 pickleable。线程模块不会发生这种情况。

  2. process.terminate()第一次尝试后并没有真正起作用。第二次或第三次尝试只是挂起解释器,可能是因为数据结构已损坏(在 API 中提到,但这没什么安慰)。

于 2009-01-12T01:43:08.473 回答
0

也许xhost +在从同一个 shell 调用你的程序之前调用 shell 命令会起作用?

我猜你的问题在于X-server。

于 2009-01-04T06:54:20.060 回答