【问题标题】:Use system() with a variable in Qt在 Qt 中使用带有变量的 system()
【发布时间】:2014-05-23 12:28:47
【问题描述】:

我想在 Qt 中运行一个系统命令,例如:

system("echo 50 > //sys//class//pwm-sunxi//pwm0//duty_percent")

现在的问题是,我想为上面代码中的 50 使用一个变量,以便我可以使用滑块来更改值

如果有帮助,我正在 Cubieboard A20 上运行 Linux Debian 发行版

我试过了

system("echo "INTtoString(variable)" > //sys//class//pwm-sunxi//pwm0//duty_percent")

但它显示错误

预计) 之前是INTtoString

有什么想法吗?

【问题讨论】:

  • 查看QProcess 以了解 Qt 运行 shell 命令的方式。实际上,更喜欢在 Qt 应用程序中使用 QFile 直接写入文件。

标签: c++ linux qt system qstring


【解决方案1】:

首先,我将使用 QFile 进行此写入操作。

如果你真的想坚持当前的概念,我个人会使用两件事:

1) QString's arg() method 创建字符串。

2) qPrintable(myQString) 获取 const char* 以供执行。

所以,我会这样写:

QString myString = QString("echo %1 > /sys/class/pwm-sunxi/pwm0/duty_percent").arg(INTtoString(variable));
system(qPrintable(myString));

但实际上,这里有一个更好的方法:

QFile file("/sys/class/pwm-sunxi/pwm0/duty_percent");
if (file.open(QIODevice::WriteOnly | QIODevice::Text
              | QIODevice::Truncate | QIODevice::Unbuffered))
    if (file.write(INTtoString(variable)) != 2)
        qDebug() << "Failed to write all:" << file.errorString();
else
    qDebug() << "Failed to open:" << file.errorString();
// No need to close as it will be done automatically by the RAII feature

还请注意,双斜杠是多余的。

【讨论】:

  • QFile 没有缓冲吗?因此应该刷新或关闭以检测实际写入系统调用的错误。 (而不是反对选民。)
  • @hyde: close 将在你用完范围时自动调用,但我同意在无缓冲模式下写入 sysfs 更好,所以我将它添加到标志中,谢谢!跨度>
【解决方案2】:

要避免 shell 调用,只需使用 QFile:

void change_duty_percent(int value)
{
  QFile duty_pc("/sys/class/pwm-sunxi/pwm0/duty_percent");
  duty_pc.open(QIODevice::WriteOnly | QIODevice::Truncate);
  duty_pc.write(QString::number(value));
  duty_pc.close();
}

如果您确实想使用 shell,请确保使用 QByteArray 的单独实例正确转换为 char*

QString command = QString("echo %1 > /sys/class/pwm-sunxi/pwm0/duty_percent").arg(value);
QByteArray commandBA(command.toLocal8Bit());
system(commandBA.data());

【讨论】:

  • 不检查错误,也关闭是不必要的......字节数组也是不必要的。它也没有使用 INTtoString OP 在他的代码中显示的内容。
  • 另外,这里的 constData() 会比 data() 更好,因为它没有被修改,但是 qPrintable 已经做了所有的样板......
  • 正如@hyde 在我的回答下的评论中提到的那样,最好像 write(2) 一样以无缓冲模式编写 sysfs。人们通常不会为此使用 fwrite(3)。
  • @LaszloPapp QByteArray 不是不必要的,请参阅How can I convert a QString to char* and vice versa?,尤其是“在调用 data() 之前必须存储字节数组”这一行。使用qPrintable 是有效的,但你必须小心不要存储返回值。
  • 1) 尝试打印出QString s = "foo"; printf("%s", s.toLocal8Bit().constData()); 您可能会感到惊讶,因为它可以在没有明确的临时 QBA 的情况下工作。我建议修复维基页面,因为它也应该可以工作。 2)这里没有存储返回值,所以它适用于这种情况。
【解决方案3】:

创建一个 QString 来保存命令:

QString command = QString("echo %1 > //sys//class//pwm-sunxi//pwm0//duty_percent");

那么您可以使用arg 将 %1 替换为另一个值:

system(command.arg(50).toLocal8Bit().constData());

【讨论】:

  • 如果有人仍然想知道这个答案也有效。谢谢棘轮怪胎,但我想我会使用 QFile 方法
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-06-21
  • 1970-01-01
  • 2012-06-09
  • 2023-03-19
  • 1970-01-01
  • 2018-06-09
  • 2018-10-21
相关资源
最近更新 更多