2011-01-20 192 views
0

我一直在嘗試從C++調用另一個程序,並將該程序的stout保存爲文本文件。 popen()似乎是合適的功能,但將其保存到文本文件不起作用。將popen()輸出寫入文件

 ofstream delaunayfile; 
    delaunayfile.open ("triangulation/delaunayedpoints.txt"); 
     FILE *fp; 
     fp = popen("qdelaunay < triangulation/rawpoints.txt", "r"); 
    delaunayfile << fp; 
    delaunayfile.close(); 

任何幫助?提前致謝!

回答

0

有兩種方法可以做到這一點:最簡單的方法

int rc = system("qdelaunay <triangulation/rawpoints.txt>triangulation/delaunayedpoints.txt"); 

和稍微複雜的方式,使用fork()的,DUP2()和execve的(),無殼解釋安裝後的工作在系統上。鑑於這看起來像你正在做計算工作,我懷疑這不是一個嵌入式系統,所以你可以假設一個工作shell。

0

popen打開一個管道,但我不知道你可以將它流入delaunayfile這種方式。

當然,如果你能做到這一點,它會非常好,它會從管道讀取,直到它完成。

檢查管道數據的正常方法是使用select()。我發現了一個有用的鏈接http://codenewbie.com/forums/threads/2908-Using-std-fstream-in-a-pipe,它集成了fstream管道,它可以幫助你實現你想要的。

在這個例子中,雖然所有你想要做的是將輸出寫入文件,爲什麼不重定向進程的輸出到它而不是管道?管道的目的是進程間通信,但您的進程似乎並未使用從其他進程收到的數據用於任何實際目的。

2

您不能直接將FILE*寫入流中。它會寫入一個內存地址而不是實際的文件內容,因此它不會給你想要的結果。

理想的解決方案是讀取ifstream並寫入您的ofstream,但無法從FILE*構建ifstream

但是,我們可以擴展streambuf類,使其工作在FILE*之上,然後將其傳遞給istream。快速搜索發現有人已經實施了該功能,並正確命名爲popen_streambuf。見this specific answer。然後

您的代碼應該是這樣的:

std::ofstream output("triangulation/delaunayedpoints.txt"); 
popen_streambuf popen_buf; 
if (popen_buf.open("qdelaunay < triangulation/rawpoints.txt", "r") == NULL) { 
    std::cerr << "Failed to popen." << std::endl; 
    return; 
} 
char buffer[256]; 
std::istream input(&popen_buf); 
while (input.read(buffer, 256)) { 
    output << buffer; 
} 
output.close(); 

正如在評論中指出的Simon Richter,有一個operator<<接受streambuf和到達EOF,直到將數據寫入ostream。這樣一來,代碼將被簡化爲:

std::ofstream output("triangulation/delaunayedpoints.txt"); 
popen_streambuf popen_buf; 
if (popen_buf.open("qdelaunay < triangulation/rawpoints.txt", "r") == NULL) { 
    std::cerr << "Failed to popen." << std::endl; 
    return; 
} 
output << &popen_buf; 
output.close(); 
+1

注意,在你的榜樣,你也可以使用`輸出<<&popen_buf;`來複制數據,因爲有一個`運營商<<(STD :: ostream&,std :: streambuf *);`。 – 2011-01-20 11:36:47