问题描述
我在 Python 中运行一个多处理系统,我计划将终端窗口划分为 4 个象限,并在其中一个象限中显示每个进程的输出。
所以,最终的输出应该是这样的:
----------------------------------
| | |
| PROCESS_01 | PROCESS_02 |
| | |
----------------------------------
| | |
| PROCESS_03 | PROCESS_04 |
| | |
----------------------------------
if __name__ == "__main__":
set_start_method("spawn")
p01 = mp.Process(target=p01_Initializer,args=(...))
p01.daemon = True
p01.start()
p02 = mp.Process(target=p02_Initializer,args=(...))
p02.daemon = True
p02.start()
p03 = mp.Process(target=p03_Initializer,args=(...))
p03.daemon = True
p03.start()
p04 = mp.Process(target=p04_Initializer,args=(...))
p04.daemon = True
p04.start()
我打算使用curses模块来实现这种可视化。
基本上在每个过程中我都创建了一个不同的窗口。两者具有相同的高度/宽度(rows_mid,cols_mid),但其想法是进程 01 的窗口应起源于 (0,0),而进程 02 的窗口应起源于坐标 (0,cols_mid),如下所示:>
PROCESS_01
curses.initscr()
cols_tot = curses.COLS
rows_tot = curses.LInes
x_mid = int(0.5*cols_tot)
y_mid = int(0.5*rows_tot)
self.win = curses.newwin(y_mid,x_mid,0)
self.win.addstr(0,"*** PROCESS 01 ***")
self.win. addstr(whatever)
PROCESS_02
curses.initscr()
cols_tot = curses.COLS
rows_tot = curses.LInes
x_mid = int(0.5*cols_tot)
y_mid = int(0.5*rows_tot)
self.win = curses.newwin(y_mid,x_mid)
self.win.addstr(0,"*** PROCESS 02 ***")
self.win. addstr(whatever)
但它并没有真正起作用。一开始,只有 PROCESS_02 的输出被可视化,在正确的位置。 然后,只有 PROCESS_01 出现,但一些东西在 PROCESS_02 的输出应该是的空间中可视化,就像这样
我能以某种方式修复它吗?有没有比使用诅咒更好/更简单的替代方法?
解决方法
如评论中所述:
-
我可以通过将输出写入日志文件并使用 tmux 以更简单的方式获得相同的结果;
-
如果您想坚持使用“手动”方法,问题似乎是各个进程相互干扰,因此屏幕会被每个进程覆盖。
我通过将每个进程的所有输出收集在一个数组中来解决它,然后通过队列将其发送回主进程并在那里打印。
PROCESS_01
output_messages_01 = []
output_messages_01.append('first output of P01')
output_messages_01.append('second output of P01')
....
## limiting overall number of messages in the array (if too many,it gets out of the window row limit when printing them in terminal)
if len(output_messages_01)>15:
output_messages_01 = output_messages_01[-15:]
output_queue_p01.put((output_messages_01))
PROCESS_02
output_messages_02 = []
output_messages_02.append('first output of P02')
output_messages_02.append('second output of P02')
....
if len(output_messages_02)>15:
output_messages_02 = output_messages_02[-15:]
output_queue_p02.put((output_messages_02))
并且,在主要过程中,我收集并打印所有内容
主要流程
## creating panels
win11 = curses.newwin(rows_mid,cols_mid,0)
win12 = curses.newwin(rows_mid,cols_mid)
win21 = curses.newwin(rows_mid,rows_mid,0)
win22 = curses.newwin(rows_mid,cols_mid)
win11.addstr(0,"*** PROCESS 01 ***",curses.A_BOLD)
win12.addstr(0,"*** PROCESS 02 ***",curses.A_BOLD)
win21.addstr(0,"*** PROCESS 03 ***",curses.A_BOLD)
win22.addstr(0,"*** PROCESS 04 ***",curses.A_BOLD)
## getting array with output message from process01
p01_messages = output_queue_p01.get()
for row,message in enumerate(p01_messages):
win11.addstr(row,message)
win11.clrtoeol()
## getting array with output message from process02
p02_messages = output_queue_p02.get()
for row,message in enumerate(p02_messages):
win12.addstr(row,message)
win12.clrtoeol()
## same thing for processes 03 and 04 ...
win11.refresh()
win12.refresh()
win21.refresh()
win22.refresh()
其他进程类似