如何在 C++ 中实时绘制 Gnuplot 中的图形?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/4445720/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to plot graphs in Gnuplot in Real time in C++?
提问by chutsu
I'm trying to plot a graph in real time using GNUplot and C++. Does anyone know of any good libraries that does this? Thanks
我正在尝试使用 GNUplot 和 C++ 实时绘制图形。有谁知道有什么好的图书馆可以做到这一点?谢谢
采纳答案by Ben Voigt
gnuplot supports input via pipes (on windows, there's a separate executable for this, pgnuplot
). Then your program can send new commands to gnuplot, such as replot
, just as if you were typing them into the gnuplot interface directly.
gnuplot 支持通过管道输入(在 Windows 上,有一个单独的可执行文件,pgnuplot
)。然后您的程序可以向 gnuplot 发送新命令,例如replot
,就像您直接在 gnuplot 界面中键入它们一样。
How you set up the pipe connection and write to the sending end of the pipe from your C++ program varies by operating system, so you'll have to tell us what you're using if you want more help.
您如何设置管道连接并从 C++ 程序写入管道的发送端因操作系统而异,因此如果您需要更多帮助,则必须告诉我们您正在使用什么。
On Windows, there's CreatePipe
and then you set the hStdInput
element of the STARTUPINFO
struct you pass to CreateProcess
. Ditto with hStdOutput
if you need the status messages from pgnuplot
.
在 Windows 上,CreatePipe
然后设置传递给hStdInput
的STARTUPINFO
结构元素CreateProcess
。同上用hStdOutput
,如果你需要从状态信息pgnuplot
。
On POSIX (Unix, Linux, Mac OSX, etc), you can just use popen
as the quick way to get a unidirectional connection. For bidirectional, it works more like on Windows: pipe
to get handles to the ends, then fork
and in the child process call dup2
to associate stdin and stdout with the pipe, then exec
to have gnuplot
replace the child process, keeping the pipes you set up.
在 POSIX(Unix、Linux、Mac OSX 等)上,您可以将其popen
用作获得单向连接的快捷方式。对于双向的,它的工作原理更像是在Windows上:pipe
获得句柄两端,然后fork
在子进程调用dup2
到副stdin和stdout与管道,再exec
有gnuplot
更换子进程,让你设置的管道。
EDIT: From the gnuplot documentation:
编辑:从gnuplot 文档:
The special filename '-'specifies that the data are inline; i.e., they follow the command. Only the data follow the command; plotoptions like filters, titles, and line styles remain on the plotcommand line. This is similar to << in unix shell script, and $DECK in VMS DCL. The data are entered as though they are being read from a file, one data point per record. The letter "e" at the start of the first column terminates data entry. The usingoption can be applied to these data — using it to filter them through a function might make sense, but selecting columns probably doesn't!
特殊文件名“-”指定数据是内联的;即,他们遵循命令。只有数据跟随命令;绘图选项(如过滤器、标题和线条样式)保留在绘图命令行中。这类似于 unix shell 脚本中的 << 和 VMS DCL 中的 $DECK。输入数据就像从文件中读取数据一样,每条记录一个数据点。第一列开头的字母“e”终止数据输入。在使用使用它通过一个函数来过滤它们可能是有意义的,但选择列可能不-选项可以应用到这些数据!
回答by Luis G. Costantini R.
Have you tried gnuplot interfaces in ANSI C?, this is an interface for C but in the same links there are some interface for C++. Or you could try PlPlot.
您是否尝试过ANSI C 中的 gnuplot 接口?,这是 C 的接口,但在相同的链接中有一些 C++ 的接口。或者你可以试试PlPlot。
回答by dima
Look at http://search.cpan.org/~dkogan/feedGnuplot-1.08/bin/feedGnuplotThis is a commandline utility, but also works well if controlled from a program.
查看http://search.cpan.org/~dkogan/feedGnuplot-1.08/bin/feedGnuplot这是一个命令行实用程序,但如果由程序控制也能很好地工作。
回答by Arafangion
If you're interested in soft-realtime plotting, you're probably best of using a hardware accelerated graphics api (such as OpenGL), and plotting the chart yourself.
如果您对软实时绘图感兴趣,您可能最好使用硬件加速图形 api(例如 OpenGL),并自己绘制图表。
回答by Ed Daw
In my C++ code, this worked (on mac OsX mavericks, using g++ Apple LLVM version 5.0):
在我的 C++ 代码中,这有效(在 mac OsX 小牛上,使用 g++ Apple LLVM 5.0 版):
#include <sys/types.h>
#include <unistd.h>
...
// ready to make a plot
pid_t childpid=fork();
if(childpid==0) {
// child process makes plot
std::FILE* pipehandle=popen("gnuplot -persist","w");
// make some plot. You can send multiple commands to the pipe each ending in \n
std::fprintf(pipehandle,"plot \"results.txt\" using 1:2 with lines\n");
std::fprintf(pipehandle,"quit\n");
std::fflush(pipehandle);
std::fclose(pipehandle);
// child process exits
exit(0);
}
// parent process waits for child process to exit
waitpid(childpid,NULL,0);
// you can now repeat to make other gnuplots; all will appear simultaneously in the
// terminal and are persistent after the parent process has finished.