Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/302.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 如何使用多线程执行子流程_Python_Python 3.x_Tkinter - Fatal编程技术网

Python 如何使用多线程执行子流程

Python 如何使用多线程执行子流程,python,python-3.x,tkinter,Python,Python 3.x,Tkinter,此程序在一个小画布上工作并显示服务器延迟,但由于ping服务器和显示pingdef display():需要程序时间,因此在子进程完成之前,无法拖动窗口类WindowDragable():,因此拖动窗口时存在延迟。是否可以通过多线程解决此延迟,以便平滑拖动窗口 from tkinter import * from PIL import ImageTk, Image import subprocess import _thread host = "141.101.115.212" #host I

此程序在一个小画布上工作并显示服务器延迟,但由于ping服务器和显示ping
def display():
需要程序时间,因此在子进程完成之前,无法拖动窗口
类WindowDragable():
,因此拖动窗口时存在延迟。是否可以通过多线程解决此延迟,以便平滑拖动窗口

from tkinter import *
from PIL import ImageTk, Image
import subprocess
import _thread

host = "141.101.115.212" #host IP address

root = Tk()
root.overrideredirect(1)
im = Image.open("image.png")
width, height = im.size
canvas = Canvas(root, width=width, height=height)
canvas.pack()
image = ImageTk.PhotoImage(file="image.png")
canvas.create_image(0, 0, image=image, anchor=NW)
text = canvas.create_text(125, 75, anchor=CENTER)

def display():
    global text
    #Launches 'command' windowless and waits until finished; finds ping
    suinfo = subprocess.STARTUPINFO()
    suinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
    x = subprocess.Popen(["ping.exe", "141.101.115.212"], stdout=subprocess.PIPE, startupinfo=suinfo)
    #find latency with regex
    x = str(x.communicate()[0])
    lhs, rhs = x.split("Average = ")
    lhs, rhs = rhs.split("\\", 1)
    lhs, rhs = lhs.split("m")
    if int(lhs) > 999:
        lhs = "999" + "ms"
    latency = lhs
    canvas.itemconfig(text, text=latency, width=width)
    canvas.itemconfig(text, font=("courier", 25, "bold"))
    canvas.itemconfig(text, fill="white")
    root.after(1000, display)


class WindowDraggable():

    def __init__(self, label):
        self.label = label
        label.bind('<ButtonPress-1>', self.StartMove)
        label.bind('<ButtonRelease-1>', self.StopMove)
        label.bind('<B1-Motion>', self.OnMotion)

    def StartMove(self, event):
        self.x = event.x
        self.y = event.y

    def StopMove(self, event):
        self.x = None
        self.y = None

    def OnMotion(self,event):
        x = (event.x_root - self.x - self.label.winfo_rootx() + self.label.winfo_rootx())
        y = (event.y_root - self.y - self.label.winfo_rooty() + self.label.winfo_rooty())
        root.geometry("+%s+%s" % (x, y))

label = Label(root, text='drag me')
WindowDraggable(label)
label.pack()
#_thread.start_new_thread( print_time, ("Thread-2", 4, ) )
root.after(0, display())
root.mainloop()
从tkinter导入*
从PIL导入ImageTk,图像
导入子流程
导入线程
host=“141.101.115.212”#主机IP地址
root=Tk()
root.overrideredirect(1)
im=Image.open(“Image.png”)
宽度、高度=im尺寸
画布=画布(根,宽度=宽度,高度=高度)
canvas.pack()
image=ImageTk.PhotoImage(file=“image.png”)
canvas.create_image(0,0,image=image,anchor=NW)
文本=画布。创建文本(125,75,锚定=中心)
def display():
全局文本
#无窗口启动“命令”并等待完成;找到平
suinfo=subprocess.STARTUPINFO()
suinfo.dwFlags |=subprocess.STARTF_USESHOWWINDOW
x=subprocess.Popen([“ping.exe”,“141.101.115.212”],stdout=subprocess.PIPE,startupinfo=suinfo)
#使用正则表达式查找延迟
x=str(x.communicate()[0])
lhs,rhs=x.split(“Average=”)
lhs,rhs=rhs.split(“\\”,1)
左侧,右侧=左侧拆分(“m”)
如果int(lhs)>999:
lhs=“999”+“ms”
延迟=lhs
canvas.itemconfig(text,text=latency,width=width)
canvas.itemconfig(文本,字体=(“courier”,25,“粗体”))
canvas.itemconfig(text,fill=“white”)
root.after(1000,显示)
类WindowDraggable():
定义初始化(自我,标签):
self.label=标签
label.bind(“”,self.StartMove)
label.bind(“”,self.StopMove)
label.bind(“”,self.OnMotion)
def StartMove(自身、事件):
self.x=event.x
self.y=event.y
def停止移动(自身、事件):
self.x=无
self.y=None
def OnMotion(自身、事件):
x=(event.x_root-self.x-self.label.winfo_rootx()+self.label.winfo_rootx())
y=(event.y_root-self.y-self.label.winfo_rooty()+self.label.winfo_rooty())
根几何体(“++%s++%s”%(x,y))
label=label(根,text='drag me')
WindowDragable(标签)
label.pack()
#_线程。启动新线程(打印时间,(“线程2”,4,))
root.after(0,display())
root.mainloop()

与其尝试对抗Tkinter的内置循环/线程,不如使用它:

def wait_for_it(proc):
    proc.poll()
    if proc.returncode is None:                      # subprocess hasn't finished yet
        root.after(100, lambda: wait_for_it(proc))   # register a callback for 100ms
    else:
        display(proc.communicate()[0])


def display(x):
    lhs, rhs = x.split("Average = ")
    # the rest of your code goes here...

# instead of root.after(0, display)
wait_for_it(subprocess.Popen(['ping', 'google.com']))

顺便说一句,我强烈建议您将代码粘贴到堆栈交换上,以获得一些样式指针并帮助简化它。

为什么不等到过程实际完成后再尝试与它通信?@WayneWerner我对Python(以及一般编程)还是有点陌生,我不确定您的意思。你能解释一下你的建议吗?@WayneWerner我还是迷路了……谢谢,这两个网站到底有什么区别?前者的目的是帮助整个程序,而不是故障代码片段吗?这个网站最初更具包容性。随着我们的规模越来越大,我们需要不断缩小和完善范围。所以现在有些东西可能是准主题的,要么是较少的,要么是完全脱离主题的。因此,这是一个错误驱动的网站-有些东西不工作,但我不知道为什么。CR确实适用于那些具有功能性的代码,但可以以计算机不关心的方式进行改进的代码,但其他程序员会。更多的事实检查也是如此,CR更多的是编辑。至少这是我的理解!