tkintert와 multiprocessing의 동거
12425 단어 multiprocessingTkinter파이썬(3.6)
배경
아무래도 첫 투고입니다.
저는 제쳐두고, 세상에는 많은 정보가 넘쳐납니다.
그물은 편리하지만 찾기가 어렵습니다.
뭔가 하고 싶은 것이 있어 찾고, 이것을 읽고 있는 당신, 고생님입니다.
이번 파이썬(3.6)에서 tkinter와 multiprocessing을 동거시켜 보았다는 이야기입니다만.
샘플 파일이있을 것이라고 생각하고 그물로 검색하여 하루를 부수고 포기합니다.
(일본어 정보가 너무 적지 않습니까?)
적당히 쓰기 시작하고, 뭔가 잘 모르는 느낌이 되어 하루를 보냈다.
(일급 1만이라고 하면 2만⇒좋은 마우스 정도 살 수 있어...)
앞으로 나 같은 일본인이 혼자라도 줄어들도록 이 기사를 첫 투고로 하기로 결의한 것이다.
코드를 공개하는 것은 자신의 중요한 물건을 공개하는 것이므로,
노출광이 아닌 나에게 있어서는, 당황스럽지 않지만, 용기 냅니다.
목적
전치는 이 정도로 하고, 본제입니다.
파이썬을 처음 1 년 정도 지났지만 Tkinter를 최근에 사용하기 시작했습니다.
사용자의 입력을 이벤트 트리븐에서 받기 쉽고 편리합니다.
한편, 파이썬은 pyserial이나 python-can을 사용하면 여러 가지와 쉽게 연결되므로,
IoT 시대(← 아직 사어가 되어 있지 않지요?@유비쿼터스 사회의 아이)에는, 편리하게 하고 있습니다.
pyserial이나 python-can이지만 다른 장치에서 동동 정보를 날 수 있습니다.
이 날아온 정보를 Tkinter로 처리하려고 하면 .after에서 재귀 호출을 하는 것으로 처리할 수 있습니다.
다만, 처리하는 양이 늘어나면, 그 처리에 당겨져,
모처럼의 Tkinter의 인터페이스에 확실히 감이 나옵니다.
이 엉뚱한 느낌을 없애기 위해 처리 내용을 multiprcessiong로 병렬화하자는 이야기입니다.
내용
이번 기재의 프로그램은, python3.6의 Windows, Linux에서 일단 동작은 확인이 끝났습니다.
빠른 샘플 프로그램은 다음과 같습니다.
multiTinker.pyimport multiprocessing as mp
from multiprocessing import Process,Manager
import tkinter as tk
import os
from time import sleep
class MainFrame(tk.Frame):
def __init__(self,master=None):
super().__init__(master)
self.grid()
self.MainCounter = 0
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.SubMsg = "sub:"
self.CreateWidgets()
self.afterId = self.after(1000,self.Update)
self.shareDict = Manager().dict()
self.SubProcess = Process(target=SubProcess\
, args=(self.shareDict,))
self.SubProcess.start()
def __del__(self):
print("killing me")
self.SubProcess.terminate()
def CreateWidgets(self):
self.MainLabel = tk.Label(self\
,text = str(self.MainMsg)\
,width=32)
self.MainLabel.grid(row=1,column=1)
self.SubLabel = tk.Label(self\
,text = str(self.SubMsg)\
,width=32)
self.SubLabel.grid(row=1,column=2)
def Update(self):
self.MainCounter += 1
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.MainLabel.configure(text=self.MainMsg)
self.SubMsg = "sub({}):{}".format(self.shareDict["PID"]\
,self.shareDict["val"])
self.SubLabel.configure(text=str(self.SubMsg))
self.afterId = self.after(1000,self.Update)
def SubProcess(shareDict):
i = 0
while i<1000:
i += 1
shareDict["PID"] = os.getpid()
shareDict["val"] = i
print(i)
sleep(0.1)
if __name__ == '__main__':
root = tk.Tk()
app = MainFrame(master=root)
app.mainloop()
app.__del__()
위 프로그램이 Windows에서 실행될 때의 스크린 샷은 다음과 같습니다.
명령 프롬프트에 표시되는 것은
SubProcess 함수 내에서 출력 된 print (i) 때문입니다.
그 위의 tk 윈도우는 1 초 간격의 Update 메소드로
화면을 업데이트하는 창입니다.
왼쪽은 메인 프로세스 (tkinter의 after 재귀 호출)입니다.
작성한 메시지 인 카운터 값 (괄호 안은 프로세스 ID)입니다.
오른쪽은 Sub 프로세스의 Dict에서 만든 메시지입니다.
프로그램의 상세한 내용은, 요구가 있을 것 같으면 향후 기재합니다.
주의사항
위의 샘플 프로그램은 완벽하지 않을 수 있습니다.
특히 멀티 프로세스에서 시작한 SubProcess의 끝은app.__del___()
에서 절대 문제 없을까 물어보면 멀리 보고 싶어집니다.
위 프로그램은 SubProcess를 유한 루프로 만들었지만,
통신 시스템을 처리하면 무한 루프로 변경됩니다.
그 때 언제까지 계속 작동할지는 모릅니다.
각자, 확인하면서 실장해 보세요.
Reference
이 문제에 관하여(tkintert와 multiprocessing의 동거), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/gamboling/items/69d06b467664f6b85891
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
전치는 이 정도로 하고, 본제입니다.
파이썬을 처음 1 년 정도 지났지만 Tkinter를 최근에 사용하기 시작했습니다.
사용자의 입력을 이벤트 트리븐에서 받기 쉽고 편리합니다.
한편, 파이썬은 pyserial이나 python-can을 사용하면 여러 가지와 쉽게 연결되므로,
IoT 시대(← 아직 사어가 되어 있지 않지요?@유비쿼터스 사회의 아이)에는, 편리하게 하고 있습니다.
pyserial이나 python-can이지만 다른 장치에서 동동 정보를 날 수 있습니다.
이 날아온 정보를 Tkinter로 처리하려고 하면 .after에서 재귀 호출을 하는 것으로 처리할 수 있습니다.
다만, 처리하는 양이 늘어나면, 그 처리에 당겨져,
모처럼의 Tkinter의 인터페이스에 확실히 감이 나옵니다.
이 엉뚱한 느낌을 없애기 위해 처리 내용을 multiprcessiong로 병렬화하자는 이야기입니다.
내용
이번 기재의 프로그램은, python3.6의 Windows, Linux에서 일단 동작은 확인이 끝났습니다.
빠른 샘플 프로그램은 다음과 같습니다.
multiTinker.pyimport multiprocessing as mp
from multiprocessing import Process,Manager
import tkinter as tk
import os
from time import sleep
class MainFrame(tk.Frame):
def __init__(self,master=None):
super().__init__(master)
self.grid()
self.MainCounter = 0
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.SubMsg = "sub:"
self.CreateWidgets()
self.afterId = self.after(1000,self.Update)
self.shareDict = Manager().dict()
self.SubProcess = Process(target=SubProcess\
, args=(self.shareDict,))
self.SubProcess.start()
def __del__(self):
print("killing me")
self.SubProcess.terminate()
def CreateWidgets(self):
self.MainLabel = tk.Label(self\
,text = str(self.MainMsg)\
,width=32)
self.MainLabel.grid(row=1,column=1)
self.SubLabel = tk.Label(self\
,text = str(self.SubMsg)\
,width=32)
self.SubLabel.grid(row=1,column=2)
def Update(self):
self.MainCounter += 1
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.MainLabel.configure(text=self.MainMsg)
self.SubMsg = "sub({}):{}".format(self.shareDict["PID"]\
,self.shareDict["val"])
self.SubLabel.configure(text=str(self.SubMsg))
self.afterId = self.after(1000,self.Update)
def SubProcess(shareDict):
i = 0
while i<1000:
i += 1
shareDict["PID"] = os.getpid()
shareDict["val"] = i
print(i)
sleep(0.1)
if __name__ == '__main__':
root = tk.Tk()
app = MainFrame(master=root)
app.mainloop()
app.__del__()
위 프로그램이 Windows에서 실행될 때의 스크린 샷은 다음과 같습니다.
명령 프롬프트에 표시되는 것은
SubProcess 함수 내에서 출력 된 print (i) 때문입니다.
그 위의 tk 윈도우는 1 초 간격의 Update 메소드로
화면을 업데이트하는 창입니다.
왼쪽은 메인 프로세스 (tkinter의 after 재귀 호출)입니다.
작성한 메시지 인 카운터 값 (괄호 안은 프로세스 ID)입니다.
오른쪽은 Sub 프로세스의 Dict에서 만든 메시지입니다.
프로그램의 상세한 내용은, 요구가 있을 것 같으면 향후 기재합니다.
주의사항
위의 샘플 프로그램은 완벽하지 않을 수 있습니다.
특히 멀티 프로세스에서 시작한 SubProcess의 끝은app.__del___()
에서 절대 문제 없을까 물어보면 멀리 보고 싶어집니다.
위 프로그램은 SubProcess를 유한 루프로 만들었지만,
통신 시스템을 처리하면 무한 루프로 변경됩니다.
그 때 언제까지 계속 작동할지는 모릅니다.
각자, 확인하면서 실장해 보세요.
Reference
이 문제에 관하여(tkintert와 multiprocessing의 동거), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다
https://qiita.com/gamboling/items/69d06b467664f6b85891
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념
(Collection and Share based on the CC Protocol.)
import multiprocessing as mp
from multiprocessing import Process,Manager
import tkinter as tk
import os
from time import sleep
class MainFrame(tk.Frame):
def __init__(self,master=None):
super().__init__(master)
self.grid()
self.MainCounter = 0
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.SubMsg = "sub:"
self.CreateWidgets()
self.afterId = self.after(1000,self.Update)
self.shareDict = Manager().dict()
self.SubProcess = Process(target=SubProcess\
, args=(self.shareDict,))
self.SubProcess.start()
def __del__(self):
print("killing me")
self.SubProcess.terminate()
def CreateWidgets(self):
self.MainLabel = tk.Label(self\
,text = str(self.MainMsg)\
,width=32)
self.MainLabel.grid(row=1,column=1)
self.SubLabel = tk.Label(self\
,text = str(self.SubMsg)\
,width=32)
self.SubLabel.grid(row=1,column=2)
def Update(self):
self.MainCounter += 1
self.MainMsg = "main({}):{}".format(\
os.getpid(),self.MainCounter)
self.MainLabel.configure(text=self.MainMsg)
self.SubMsg = "sub({}):{}".format(self.shareDict["PID"]\
,self.shareDict["val"])
self.SubLabel.configure(text=str(self.SubMsg))
self.afterId = self.after(1000,self.Update)
def SubProcess(shareDict):
i = 0
while i<1000:
i += 1
shareDict["PID"] = os.getpid()
shareDict["val"] = i
print(i)
sleep(0.1)
if __name__ == '__main__':
root = tk.Tk()
app = MainFrame(master=root)
app.mainloop()
app.__del__()
위의 샘플 프로그램은 완벽하지 않을 수 있습니다.
특히 멀티 프로세스에서 시작한 SubProcess의 끝은
app.__del___()
에서 절대 문제 없을까 물어보면 멀리 보고 싶어집니다.위 프로그램은 SubProcess를 유한 루프로 만들었지만,
통신 시스템을 처리하면 무한 루프로 변경됩니다.
그 때 언제까지 계속 작동할지는 모릅니다.
각자, 확인하면서 실장해 보세요.
Reference
이 문제에 관하여(tkintert와 multiprocessing의 동거), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://qiita.com/gamboling/items/69d06b467664f6b85891텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)