Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/69.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 查找popen输出更改_C_Linux_Gcc - Fatal编程技术网

C 查找popen输出更改

C 查找popen输出更改,c,linux,gcc,C,Linux,Gcc,我需要创建一个程序来执行以下操作: 用popen执行命令 用popen的输出做一些事情(在很多事情中使用该文件) 继续检查popen输出更改,如果有更改,请重新执行所有操作 源代码如下: 因此,如果popen的输出发生变化,我只想再次执行程序的所有其余部分(必须与第一个输出进行比较) 程序应该第一次执行所有操作,之后,如果popen输出发生变化,则只执行所有操作并再次打印。popen应每秒验证一次 更新 我在这里没有得到任何解决问题的答案,但在阅读C教程时,我看到了一些关于线程的内容,对我来

我需要创建一个程序来执行以下操作:

  • 用popen执行命令
  • 用popen的输出做一些事情(在很多事情中使用该文件)
  • 继续检查popen输出更改,如果有更改,请重新执行所有操作
源代码如下:

因此,如果popen的输出发生变化,我只想再次执行程序的所有其余部分(必须与第一个输出进行比较) 程序应该第一次执行所有操作,之后,如果popen输出发生变化,则只执行所有操作并再次打印。popen应每秒验证一次

更新
我在这里没有得到任何解决问题的答案,但在阅读C教程时,我看到了一些关于线程的内容,对我来说这听起来像是解决方案,我会看看我能做些什么。

您可以根据需要随时调用
popen()
。但是,要正确释放调用
popen()
所使用的资源,您需要调用
pclose()

在您的情况下,您可能希望偶尔轮询输出,并在必要时发出一些消息

first_time = 1;
need_to_print = 1;
for (;;) {
    FILE *fp = popen(...);
    /* read input ... */
    pclose(fp);
    /* parse input ... */
    if (first_time) {
        /* save contents for future comparison... */
        first_time = 0;
    } else {
        need_to_print = /* result of comparing saved contents with new contents */;
    }
    if (need_to_print) {
        /* print something ... */
    }
    sleep(INTERVAL);
}
你可以用 //由2个字符串缓冲区组成的数组 字符输出[2][1024]; //正在使用的字符串缓冲区索引 int flip=0; 文件*fp

void executeTestCommand() {


    int resultSize;
    fp = popen("free -m | awk 'NR==3 {print $3}'" "r");
    if (fp == NULL) {
        perror("Failed to run command");
    }
    else {
        result_size = fread(output, 1, 1024 - 1, fp);
        //place string terminator
        output[flip][result_size] = '\0';
    }
    //flip the buffers
    flip = flip ^ 1;
    pclose(fp);
}


int main() {
    //init with empty string
    output[0][0] = '\0';
    output[1][0] = '\0';
    //for ever
    for(;;) {
        executeTestCommand();
        //if the last command output differs from the current
        //command output
        if (strcmp(output[0], output[1])) {
            //execute the rest of the command here
        }           
    }

    return 0;
}
干杯

您希望关闭文件指针(您不希望出现任何内存泄漏),因为您将在popen中再次使用相同的file*fp变量


稍后编辑:希望有帮助:)。您可能希望在for ever块中插入一个sleep语句,因为这将占用大量cpu。

@AlinUngureanu@JonathanLeffler@jxh

我在git上发布了源代码!现在你可以看到我想要什么了


一种可能更简单、更精简的方法是读取
/proc/meminfo
,使用
sscanf()
fscanf()
从第二行(“MemFree”)中提取值并除以1024。这就是
free
从中获取数字的地方。这个命令只是一个示例,在这个示例中,我可以通过读取文件来获取值。但是假设我不能,你的情况我不清楚。似乎您希望运行一个命令(仅在问题中使用示例),并记录输出的确切内容,并在完成之前根据输出进行处理。此外,在从第一次调用读取所有数据后的某个时间,您希望启动命令的新副本,再次读取数据,边处理边记录新内容是否与旧内容相同。如果这就是你想要的,迭代之间的延迟是多少?第二次处理是否应该在输出没有变化的情况下进行?@JonathanLeffler再次编辑,看看你是否理解。因此,在第二次(或任何后续)迭代中,它必须读取命令的所有输出,将其与之前得到的结果进行比较,如果当前迭代有差异,则重新执行操作。在第一次迭代中读取完所有数据后再执行这些操作可以吗(如果不行,为什么不可以,因为“读取命令的所有输出”和“如果有任何不同,请处理此迭代的输出”将更容易管理整个堆)。但是如果我在程序的其余部分在很多事情中使用该文件,你认为把程序的其余部分都放在循环中是个好主意吗?
readinput…
comment意味着将所有输入读入缓冲区。然后用
pclose()关闭
fp
。之后,使用缓冲区来存储所需的内容。您不需要保留该文件。@HenriqueLengler:您的更新不清楚。如果输出与第一次执行不同,则表示只希望再次执行该命令。但是,除非你真的再次执行,否则你怎么知道某些东西已经改变了呢?我想你对自己的要求感到困惑。你能再澄清一次吗?也许用一个真实的例子来说明一个问题,这个问题实际上需要按照你所描述的方式来解决吗?@jhk不,我的意思是每次都执行popen命令,但只有在发生变化时才执行其余的命令。正如我在这里所说,“如果popen的输出发生了变化,那么我只想再次执行程序的所有剩余部分”@jhx(;;)的作用是什么?我只能在这里进行注释,所以你只想在
cmus remote-Q
返回与上次不同的内容时执行剩余部分?正是这样。我想每秒钟查看一下命令输出中的更改,如果有更改,请重新执行其他命令。虽然提供完整的源代码可能会有所帮助,但出于您的问题的目的,将人们引向外部源通常不是一个好主意。文章应该有一个简明的问题,文章中的所有相关代码,如果合适的话,你的编译字符串显示构建标志,请求的警告和使用的库,以及任何相关的错误消息,以及必要的示例输入和输出。这样你会得到更多的帮助。@DavidC.Rankin在这里粘贴代码太可怕了,我需要在任何代码行之前删除4个空格。我同意你的看法。准备发布代码的一种简单方法(如果您的编辑器不会自动执行)就是使用
sed
。它适用于任何文本文件。只需:
sed-e的/^/'
当然,您也可以将其重定向到临时文件以在编辑器中打开:
sed-e的/^/'tempfile
HTH(即
sed
命令的第二部分中的4个空格)