Python脚本无法从Qt完全运行

问题描述 投票:-1回答:1

我想从Qt运行一个python脚本。我可以用QProcess调用它并获取qDebug()来打印python脚本打印的内容。但由于某些原因,我无法在代码中的某个点之后读取任何python脚本的打印件。

有谁知道如何解决这个问题?非常感谢你提前。这是我的第一个问题,所以如果我做错了,我很抱歉。

我的widget.cpp文件和python脚本如下。 (python脚本位于Qt程序的目录中。)

我的widget.cpp文件:

#include "widget.h"
#include "ui_widget.h"
#include "QDebug"
#include <QTimer>
#include <QProcess>
#include <QDir>


Widget::Widget(QWidget *parent) :
    QWidget(parent),
    ui(new Ui::Widget)
{
    ui->setupUi(this);
    QTimer *timer = new QTimer(this);
    connect(timer, SIGNAL(timeout()), this, SLOT(checkTexts()));
    timer->start(5000);
}

Widget::~Widget()
{
    delete ui;
}


void Widget::checkTexts()
{
    //QProcess process; //I also tried this way with the same results
    QProcess *process = new QProcess(this);

    QStringList arguments { QCoreApplication::applicationDirPath() + "/../../../../../Folder/Qt Desktop Application/ApplicationFiles/PullText.py"};

    process->start("python", arguments);
    process->waitForFinished(-1);

    QString output = process->readAll();
    process->close();
    qDebug() << output;
}

我的Python脚本(PullText.py)应该将一行文本文件发送到我的Qt应用程序:

newMessageSplitter = "***\n"

#print "1" #this prints in the qDebug() << output

file = open("texts.txt","r")

#print “2” #this doesn't print

texts = file.read()

x = texts.find(newMessageSplitter) + len(newMessageSplitter)
singleLine = texts[:x-len(newMessageSplitter)]
file.close()
file = open("texts.txt","w")
file.write(texts[x:])
file.close()

#print singleLine #this is what I want to send to the output but it doesn't get sent to Qt
python c++ qt
1个回答
0
投票

我认为你的问题在这里:

process->waitForFinished(-1);

如果您的子进程产生的输出数量超过少量,则调用waitForFinished()会出现问题,因为如果您的子进程的stdout输出缓冲区填满,则会出现死锁情况:现在阻止了子/ Python进程等待缓冲区耗尽,以便它可以写更多的输出;同时,您的Qt /父进程也被阻止,等待子进程退出。

由于这两个进程都无法执行任何操作,因此子进程永远不会退出,因此waitForFinished()永远不会返回,并且您的程序将永远停留。

(另一种可能是子进程被设置为在其stdout缓冲区填满时简单地丢弃任何其他输出文本;在这种情况下,子进程将退出并且waitForFinished()将返回,但是您的process->readAll()调用将仅返回初始输出文本能够适应输出缓冲区;剩下的文本被丢弃,所以你的Qt进程永远不会看到它)

在任何一种情况下,解决方案都不是在waitForFinished()内部等待,而是立即调用readAll()来收集其输出而无需等待。您可能需要在循环中调用它,直到子进程退出,可能还有waitForReadyRead()以避免繁忙循环。

© www.soinside.com 2019 - 2024. All rights reserved.