如何从一个Python脚本启动另一脚本并在控制台显示其运行进度
Python父脚本实时显示子脚本运行进度的实现方案
完全可以实现,核心逻辑是父脚本启动子脚本时捕获其标准输出/错误流,或者通过进程间通信获取进度数据,以下是3种常用的落地方案:
方案1:实时捕获子脚本标准输出(无需修改子脚本核心逻辑)
这是通用度最高的方案,只要子脚本本身会向控制台打印进度内容,父脚本通过subprocess模块实时读取输出即可同步显示。
父脚本示例代码:
import subprocess import sys # 启动子Python脚本 sub_proc = subprocess.Popen( [sys.executable, "your_sub_script.py"], stdout=subprocess.PIPE, stderr=subprocess.STDOUT, # 合并错误流和输出流,也可单独捕获stderr bufsize=1, text=True, encoding="utf-8", env={"PYTHONUNBUFFERED": "1"} # 强制关闭子脚本输出缓冲,保证实时性 ) # 逐行读取子脚本输出并打印到当前控制台 for output_line in iter(sub_proc.stdout.readline, ""): if output_line: # 可在此处添加自定义逻辑,比如提取百分比、格式化展示 print(output_line.strip(), flush=True) # 等待子进程执行结束,获取返回码 return_code = sub_proc.wait() print(f"子脚本执行完成,返回码:{return_code}")
如果子脚本用\r实现同一行动态更新的进度条,只要去掉strip()处理即可正常显示动态效果。
方案2:通过队列传递结构化进度数据(适合自有脚本二次开发)
如果需要精准获取进度百分比、当前执行任务这类结构化数据,不用解析打印的字符串,可以通过进程间队列传递进度信息:
父脚本代码
from multiprocessing import Process, Queue import your_sub_script def run_sub_task(queue): your_sub_script.main(progress_queue=queue) if __name__ == "__main__": progress_queue = Queue() sub_process = Process(target=run_sub_task, args=(progress_queue,)) sub_process.start() while sub_process.is_alive() or not progress_queue.empty(): if not progress_queue.empty(): progress_info = progress_queue.get() # 可自定义进度渲染逻辑,比如对接tqdm生成进度条 print(f"进度:{progress_info['percent']}% | 当前任务:{progress_info['task']}", end="\r", flush=True) sub_process.join() print("\n子脚本执行完毕")
子脚本对应修改
def main(progress_queue=None): total_task_count = 100 for i in range(total_task_count): # 你的业务执行逻辑 if progress_queue: # 推送结构化进度数据 progress_queue.put({ "percent": i + 1, "task": f"处理第{i+1}项任务" })
方案3:第三方进度库直接联动
如果子脚本本身使用tqdm这类进度条库,默认输出会直接打到标准输出,用方案1的捕获逻辑即可直接正常显示动态进度条,无需额外修改。
注意事项
- 无法修改子脚本代码时优先选择方案1,只要子脚本有打印进度的行为即可正常捕获
- 子脚本输出有延迟时,优先检查是否开启了输出缓冲,添加
PYTHONUNBUFFERED环境变量即可解决 - 需要对进度做二次处理(如存日志、上报监控)时,优先选择方案2获取结构化数据
内容的提问来源于stack exchange,提问作者Aladin
相关产品推荐
相关产品推荐

