1

私のプログラムから別のプログラムからの出力を読み取る必要があります。そのために、popen()を使用できます。このようにして、プログラムで解析できるファイル*をプログラムの出力に取得します。プログラムからpopen()の戻り値の内容を読み取って解析するにはどうすればよいですか?あるいは、どこかにもっとC ++のようなバージョンのpopenがありますか?

4

2 に答える 2

3

と道徳的に等価なストリーム バッファを作成するかpopen()、ストリーム バッファ ラッピングを作成することができますFILE*。ストリーム バッファを取得したら、目的とstd::istream思われる方法で使用できます。からの単純な (そしてテストされていない) ストリーム バッファの読み取りは、次のFILE*ようになります。

struct FILEbuf
    : std::streambuf {
    FILEbuf(FILE* fp): fp_(fp) {}
    int underflow() {
        if (this->gptr() == this->egptr()) {
            int size = fread(this->buffer_, 1, s_size, this->fp_);
            if (0 < size) {
                this->setg(this->buffer_, this->buffer_, this->buffer_ + size);
            }
        }
        return this->gptr() == this->egptr()
            ? traits_type::eof()
            : traits_type::to_int_type(*gptr());
     }
     FILE* fp_;
     enum { s_size = 1024 };
     char  buffer_[s_size];
};

何かを間違って入力したと思いますが、大まかに言えば、アイデアはうまくFILE*いきます。または、生成されたプロセスから読み取るストリームを作成します。これには、プラットフォーム固有のfork(), exec..(), pipe(),への呼び出しが 2 回必要ですclose()dup2()(おそらくここでも何かを忘れている可能性があります)、同様に実行できます。

上記のようなストリーム バッファは、たとえば次のように使用できます。

int main()
{
    FILEbuf      sbuf(fopen("pstream.cpp", "r"));
    std::istream in(&sbuf);
    for (std::string line; std::getline(in, line); ) {
        std::cout << line << '\n';
    }
}
于 2012-12-03T13:55:33.713 に答える
1

(GNU実装)またはFILE*と呼ばれるC++ラッパーがあります。標準化されたものではないと思いますが、グーグルで検索すると、多くのプラットフォームで利用できることがわかります。から返され、gcc 4.5.0でコンパイルされ、Linuxボックスでテストされたポインターでそれを使用する方法の実際の例を次に示します。stdio_filebufstdiobufstdiobufFILE*popen

#include <ext/stdio_filebuf.h>
#include <stdio.h>
#include <fstream>
#include <string>
#include <iostream>

using namespace std;

int main() {
    FILE* f = popen("ls", "r");
    __gnu_cxx::stdio_filebuf<char> fdbuf(f, std::ios::in);

    std::ifstream in;
    in.std::ios::rdbuf(&fdbuf);

    string s;
    in >> s;
    cout << s;

    pclose(f);
    return 0;
}
于 2012-12-03T14:15:36.677 に答える