I am using gcc as a compiler and gnuplot-iostream.h as a stream to combine C++ code and the gnuplot features.
What I am doing:
I try to make a fit of the data via gnuplot and extract the final fit parameters from the generated fit.log file for further processing.
What's the problem:
When executing the code like this
std::cout << "Starting to fit" << std::endl;
if (bStartFit == true)
// gp << doing stuf here;
std::cout << "Test end" << std::endl;
std::cout << "Fit is done" << std::endl;
Starting to fit
Fit is done
std::string filename = "fit.log";
if (bStartFit == true)
// Using Gnuplot for the data fit (command are parsed as the strings):
// 1. define the fit function.
gp << "f(x) = imfpZP * x**(-b) + c * x**(d) + g * x**(h) \n";
// 2. fit parameters first assumption.
gp << "b = 1.1; c = 0.5; d = 1.0; g = 2.0; h = 0.1 \n";
// 3. fit range.
gp << "fit [50:10000] f(x) 'agn.iimfp' via b,c,d,g,h \n";
// 4. set the logarithmic scale.
gp << "set logscale \n";
// 5. plot the fitted data.
gp << "plot 'agn.iimfp' w l lw 2 tit 'orig', f(x) w l lw 2 tit 'fit' \n";
std::cout << "Fit was successful" << std::endl;
// Opening the generated fit.log file to store the fit parameters:
std::cout << "FIT log is opened" << std::endl;
int lineCounter = 0;
while (std::getline(inFIT, line))
std::cout << "Total lines: " << lineCounter << std::endl;
// Getting the five lines with fit parameters from the fit.log:
std::fstream& GoToLine(std::fstream& file, unsigned int lineNumber);
GoToLine(file, lineCounter - 15);
std::cout << b_Line << std::endl;
sb >> tempStr >> tempChar >> b
// similar code to get another 4 lines
It is operating system specific. I am guessing you are on Linux (or at least on some POSIX OS). Then you really should read Advanced Linux Programming. And using strace(1) could be helpful to understand what is happening.
You could use popen(3), but you probably should explicitly use system calls (they are listed in syscalls(2)) like pipe(2), fork(2), dup2(2), execve(2), waitpid(2), etc. And very probably have some event loop (e.g. around poll(2)).
BTW, you should be aware that input output is buffered, and you probably want to be sure that your gnuplot stream is regularly flushed (so use
std::flush appropriately on it). Writing a
\n is not enough! You probably should code at least
gp << "plot 'agn.iimfp' w l lw 2 tit 'orig', f(x) w l lw 2 tit 'fit' " << std::endl;
(I have replaced some
\n inside a string with an explicit use of
I don't know much about gnuplot stream (I'm guessing it is a bit like some specialized
popen but using C++ streams), but I guess that you should the gnuplot
printerr command to communicate to your calling program the fact that a given curve has been plotted. (But then you need a genuine event loop, and you are defining a bidirectional protocol between
gnuplot and your program.).
Perhaps Qt or POCO might be relevant, because they provide some notion of event loop and processes. Perhaps you might have several threads (one managing
gnuplot and the other for the rest), but then you have synchronization issues.
(I don't understand enough what your program is supposed to do, and how you have coded it, so it is a blind guess; I feel your question is very unclear)
Read more about Inter-Process Communications.