You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Qt中QProcess无需重启子进程多次写入数据的实现方法

Qt C++父进程多次向Python子进程发送数据的解决方案

问题本质

你碰到的问题核心在于:

  • Python里for line in sys.stdin这种写法,会一直阻塞,直到读到换行符或者输入流被关闭(也就是父进程调用closeWriteChannel()发送EOF)才会返回内容
  • 不调用closeWriteChannel()时,QProcess的输出缓冲区没刷新,数据没真正传到子进程的stdin,所以Python收不到
  • 但关了写入通道就没法再给子进程发数据,这就导致只能发一次

解决方法(不用关通道,不用重启进程)

1. 父进程(Qt C++):发送后确保数据写入管道

别再调用closeWriteChannel(),改成每次发完数据后调用waitForBytesWritten(),同时每次发送的内容结尾加上换行符——这样Python那边能触发行读取,不用等EOF。

修改后的父进程代码:

if(PythonProcess.state() == QProcess::Running){
    // 第一次发送
    QString data1 = "starttttttttttttttt123";
    PythonProcess.write(data1.toUtf8()); // 用QByteArray直接转比std::string更简洁
    PythonProcess.write("\n"); // 必须加换行,让Python知道这是一行的结尾
    PythonProcess.waitForBytesWritten(); // 等待数据真正写入管道,避免留在缓冲区

    // 第二次发送(通道保持开放,直接发就行)
    QString data2 = "newwwwwoneeee";
    PythonProcess.write(data2.toUtf8());
    PythonProcess.write("\n");
    PythonProcess.waitForBytesWritten();
}

2. 子进程(Python):修正读取逻辑

你原来的嵌套循环有问题:while True套for line in sys.stdin,第一次读到EOF后for循环会结束,外层while再进去时,for line会一直阻塞。改成直接用readline()循环读取,每次有换行就会触发。

修改后的子进程代码:

import sys

while True:
    line = sys.stdin.readline()
    if not line:
        # 如果输入流被关闭(父进程退出),就退出循环
        break
    # 打印收到的内容,strip()去掉换行符
    print(f"收到: {line.strip()}")

补充说明

  • waitForBytesWritten()是阻塞到数据写入系统管道,确保子进程能及时拿到数据,避免QProcess的缓冲区积压
  • 一定要加换行符,这是Python行读取的触发条件;如果要发二进制数据或者不带换行的内容,可以自定义分隔符(比如用\0作为结束标志),然后Python那边按分隔符拆分读取
  • 测试时可以在父进程里加个按钮,每次点击就发一次数据,看子进程能不能实时收到

内容的提问来源于stack exchange,提问作者rohan099

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 00:25:56