Changeset 73 for trunk/lib/Gnuplot.h


Ignore:
Timestamp:
Mar 4, 2006, 7:10:07 PM (16 years ago)
Author:
Jari Häkkinen
Message:

Divided Gnuplot class into a basic gnuplot communication class
and a front end class specialized for svnstat.
Added option to plot stats against time or revision.
Removed gnuplot usage of temporary files.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/lib/Gnuplot.h

    r70 r73  
    66#include <cassert>
    77#include <cstdio>
    8 #include <fstream>
    98#include <list>
    109#include <stdexcept>
     10#include <sstream>
    1111#include <string>
    1212#include <vector>
     
    2525  ///
    2626  /// The Gnuplot class creates a pipe to 'gnuplot' and facilitates
    27   /// communication with the binary.
    28   ///
    29   /// Temporary files are created in directory /tmp. These temporary
    30   /// files are removed on a normal program exit.
     27  /// communication with the gnuplot binary.
    3128  ///
    3229  class Gnuplot
     
    4542
    4643    ///
    47     /// The destructor deletes all temporary files created in the
    48     /// calls to plot_xy and plot_x. If the program execution fails to
    49     /// reach this destructor the temporary files will not be removed
    50     /// from the storage area.
     44    /// The destructor, closes the pipe to the gnuplot binary.
    5145    ///
    52     ~Gnuplot(void);
     46    virtual ~Gnuplot(void);
    5347
    5448    ///
    5549    /// Send arbitrary commands to Gnuplot.
    5650    ///
    57     void command(std::string);
    58 
    59     ///
    60     /// @return input format for date
    61     ///
    62     // Peter, obsolete ?
    63     const std::string& date_input_format(void) { return date_input_format_; }
    64 
    65     ///
    66     ///
    67     ///
    68     void date_plot(const std::vector<double>& y,
    69                    const std::string& format="%y-%b-%d");
    70     ///
    71     ///
    72     ///
    73     void date_replot(const std::vector<double>& y,
    74                      const std::string& format="%y-%b-%d");
     51    void command(const std::string&);
    7552
    7653    ///
     
    9572    /// Gnuplot usage.
    9673    ///
    97     // Peter, do we have to set xdata for replot
    98     inline void
    99     plot(const std::vector<double>& y,
    100          const std::vector<double>& x=std::vector<double>())
    101     { command("set xdata"); plot(y,x,"plot"); }
     74    template <class T1, class T2>
     75    void plot(const std::vector<T1>& y, const std::vector<T2>& x)
     76    { plot(y,x,"plot"); }
     77
     78    template <class T1>
     79    void plot(const std::vector<T1>& y,
     80              const std::vector<T1>& x=std::vector<T1>())
     81    { plot(y,x,"plot"); }
    10282
    10383    ///
     
    10686    /// Gnuplot usage.
    10787    ///
    108     inline void
    109     replot(const std::vector<double>& y,
    110            const std::vector<double>& x=std::vector<double>())
    111     { command("set xdata"); plot(y,x,"replot"); }
     88    template <class T1, class T2>
     89    void replot(const std::vector<T1>& y, const std::vector<T2>& x)
     90    { plot(y,x,"replot"); }
    11291
    113     ///
    114     /// sets format of date output
    115     ///
    116     inline void set_date_format(const std::string& format)
    117     { date_output_format_ = format;}
    118 
    119     ///
    120     /// Function setting the dates. \a format must comply with strings
    121     /// in date
    122     ///
    123     inline void set_dates(const std::vector<std::string>& date,
    124                           const std::string& format="%Y-%m-%d")
    125     { date_=date; date_input_format_=format; }
     92    template <class T1>
     93    void replot(const std::vector<T1>& y,
     94              const std::vector<T1>& x=std::vector<T1>())
     95    { plot(y,x,"replot"); }
    12696
    12797  private:
     
    142112      assert(x.size()==y.size() || x.empty());
    143113      assert(plotcmd=="plot" || plotcmd=="replot");
    144       char name[]="/tmp/svnstatXXXXXX";
    145       int fd=mkstemp(name); // mkstemp return a file descriptor
    146       if (fd == -1)
    147         throw GnuplotException(std::string("Failed to get unique filename: ") +
    148                                name);
    149       // Jari would like to do something like 'std::ofstream tmp(fd);'
    150       // but has to settle for (which is stupid since the file is
    151       // already open for writing.
    152       std::ofstream tmp(name);
    153       for (size_t i = 0; i<y.size() && (i<x.size() || x.empty()); ++i )
    154         if (x.empty())
    155           tmp << y[i] << '\n';
     114
     115      std::ostringstream cmdstring;
     116      cmdstring << plotcmd << " '-' u 1:2 title '" << linetitle_ << "' with "
     117                << linestyle_ << '\n';
     118      for (size_t i=0; i<y.size(); ++i) {
     119        if (!x.empty())
     120          cmdstring << x[i] << '\t';
    156121        else
    157           tmp << x[i] << '\t' << y[i] << '\n';
    158       // Jari, here the stupidity goes beyond everything - the
    159       // ofstream must be closed as well as the file descriptor. If
    160       // not the program will exhaust the availabe number of
    161       // simultaneous open files.
    162       tmp.close();
    163       close(fd);
     122          cmdstring << i << '\t';
     123        cmdstring << y[i] << '\n';
     124      }
     125      cmdstring << "e\n";
    164126
    165       std::string cmdstring(plotcmd + " '" + name + "' u 1:2 title '" +
    166                               linetitle_ + "' with " + linestyle_ + "\n");
    167       if (x.empty())
    168         cmdstring = plotcmd + " '" + name + "' u 1 title '" +
    169           linetitle_ + "' with " + linestyle_ + "\n";
    170        
    171       command(cmdstring);
    172       // need to keep track of created files since the gnuplot command
    173       // is not executed until pclose on MacOSX, shouldn't the fflush
    174       // fix this in the command() member function?
    175       tempfiles_.push_back(name);
     127      command(cmdstring.str());
    176128    }
    177129
     
    179131                   const std::string& delimiters = ":");
    180132
    181     // need to keep track of created files since the gnuplot command
    182     // is not executed until pclose on MacOSX, shouldn't the fflush
    183     // fix this in the command() member function?
    184     std::list<std::string> tempfiles_;
    185     std::vector<std::string> date_;
    186     std::string date_input_format_;
    187     std::string date_output_format_;
    188133    std::string gnuplot_binary_;
    189134    std::string linestyle_;
Note: See TracChangeset for help on using the changeset viewer.