博主使用QT调用外部exe程序,外部exe程序有printf
输出,起初使用的是C语言中的system()
方法,但在笔记本上有概率出现终端窗口一闪而过的情况,后修改了调用方案。
1. QT调用外部exe
使用QT中的QProcess方法
cpp
#include <QProcess>
QProcess process;
QString cmd ="../test.exe 1 2";
process.start(cmd); // 启动可执行程序
process.startDeteched(cmd);
process.execute(cmd);
注意,此处启动可执行程序的方式有3种:
start
:外部程序启动后,将随主程序的退出而退出startDeteched
:外部程序启动后,当主程序退出时并不退出,而是继续运行。execute
:带阻塞
2. 无终端弹窗的解决方案
QProcess方法默认是无弹窗的,要想弹窗,需做如下设置:
cpp
QProcess process(this);
process.setCreateProcessArgumentsModifier(
[](QProcess::CreateProcessArguments *args) {
args->flags |= CREATE_NEW_CONSOLE;
args->startupInfo->dwFlags &= ~STARTF_USESTDHANDLES;
args->startupInfo->dwFlags |= STARTF_USEFILLATTRIBUTE;
args->startupInfo->dwFillAttribute = BACKGROUND_BLUE | FOREGROUND_RED | FOREGROUND_INTENSITY; // 定义终端背景及字体等颜色,可不指定.
});
process.start("../test.exe 1 2");
process.waitForStarted(); // 等待子进程执行结束
process.waitForFinished();
// process.close(); // 强制关闭子进程
注意,此处不能使用execute
方法,否则无效。对于CREATE_NEW_CONSOLE
等关键字,不是QT本身定义的内容,其被定义在Windows.h
头文件中,所以需要包含该头文件。
3. 实现进程输出信息的获取
使用readAll()
或者readAllStandardOutput()
方法实现,案例如下:
cpp
#include <QProcess>
#include <QTextCodec>
QProcess process;
process.start("../test.exe 1 2");
process.waitForFinished();
process.waitForReadyRead();
QByteArray qba = process.readAll();
QTextCodec* pTextCodec = QTextCodec::codecForName("System");
assert(pTextCodec != nullptr);
QString str = pTextCodec->toUnicode(qba);
qDebug("%s\n",str.toStdString().c_str());
参考链接:
- https://doc.qt.io/qt-5/qprocess.html#CreateProcessArgumentModifier-typedef
- https://cloud.tencent.com/developer/article/1932764?from_column=20075
- https://blog.csdn.net/kangkanglhb88008/article/details/125823353
- https://blog.csdn.net/VVBBBBB/article/details/121016042
- https://blog.csdn.net/m0_56554817/article/details/128252004