Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 10:06:39

0001 // ProgressLog.h is a part of the PYTHIA event generator.
0002 // Copyright (C) 2024 Torbjorn Sjostrand.
0003 // PYTHIA is licenced under the GNU GPL v2 or later, see COPYING for details.
0004 // Please respect the MCnet Guidelines, see GUIDELINES for details.
0005 
0006 #ifndef PROGRESSLOG_H
0007 #define PROGRESSLOG_H
0008 
0009 #include <ctime>
0010 #include <sys/times.h>
0011 #include <unistd.h>
0012 #include <string>
0013 #include <iostream>
0014 #include <iomanip>
0015 
0016 namespace Pythia8 {
0017 
0018 using namespace std;
0019 
0020 // ProgressLog is a simple helper class to monitor the progress of a run.
0021 // When used in the main event loop, it will with suitably (logarithmically)
0022 // spaced intervals, print out one line with information about the number
0023 // of events generated, two estimates (based on instantaneous and average
0024 // CPU consumption) of when the run will be completed, the host on which
0025 // the program is run and its process number.
0026 
0027 class ProgressLog {
0028 
0029 public:
0030 
0031   // Create an object for monitoring the progress of a run with NIn iterations.
0032   ProgressLog( long NIn, int maxsec = 1200) : secstep(maxsec) {
0033     init(NIn);
0034   }
0035 
0036   // Intermittently write out a line of progress information, giving
0037   // the current iteration (in the interval [0:N[ ).
0038   void operator()(int cnt) {
0039     tick(cnt + 1, N);
0040   }
0041 
0042   // Intermittently write out a line of progress information using the
0043   // internal counter.
0044   void operator()() {
0045     tick(++count, N);
0046   }
0047 
0048   // Intermittently write out a line of progress information giving
0049   // the current iteration and the total number of iterations.
0050   void tick(long i, long n) {
0051     if ( !statusTime(i, n) ) return;
0052 
0053     double fcpui = fclock();
0054     time_t timei = time(0);
0055     double ftime0 = time0;
0056     double ftime1 = time1;
0057     double ftimei = timei;
0058     double eff = 1.0;
0059     if ( ftimei > ftime1 && fcpui > fcpu1 )
0060       eff = (fcpui-fcpu1)/(ftimei-ftime1);
0061     if ( eff >= 1.0 ) eff = 0.999999;
0062     int ieff = 100*eff;
0063     double eff0 = 1.0;
0064     if ( ftimei > ftime0 && fcpui > fcpu0 )
0065       eff0 = (fcpui-fcpu0)/(ftimei-ftime0);
0066     if ( eff0 >= 1.0 ) eff0 = 0.999999;
0067     int ieff0 = 100*eff0;
0068     double fcpun = fcpu0 + (n*(fcpui-fcpu0))/i;
0069     time_t timen = (time_t)(ftimei + (fcpun-fcpui)/eff + 30.0);
0070     time_t timen0 = (time_t)(ftimei + (fcpun-fcpui)/eff0 + 30.0);
0071     char date[1024];
0072     char daten[1024];
0073     char daten0[1024];
0074     strftime(date,1024,"%y.%m.%d %H:%M",localtime(&timei));
0075     strftime(daten,1024,"%H:%M",localtime(&timen));
0076     strftime(daten0,1024,"%H:%M",localtime(&timen0));
0077     long ii = i;
0078     if ( n - i < n/10 ) ii = i - n;
0079     time_t dayn = (timen - timei)/86400;
0080     time_t dayn0 = (timen0 - timei)/86400;
0081 
0082     ostream & os = cout;
0083 
0084     if ( dayn <= 0 && dayn0 <= 0 ) {
0085       os << date << " " << setw(8) << ii << "/" << setw(9);
0086       os.setf(ios::left, ios::adjustfield);
0087       os << n << " etc:   " << daten << "[";
0088       os.setf(ios::right, ios::adjustfield);
0089       os << setw(2) << ieff << "%]   " << daten0 << "[" << ieff0 << "%] "
0090          << host << ":" << pid << endl << flush;
0091     } else {
0092       os << date << " " << setw(8) << ii << "/" << setw(9);
0093       os.setf(ios::left, ios::adjustfield);
0094       os << n << " etc: " << dayn << "+" << daten << "[";
0095       os.setf(ios::right, ios::adjustfield);
0096       os << setw(2) << ieff << "%] "
0097          << dayn0 << "+" << daten0 << "[" << ieff0 << "%] "
0098          << host << ":" << pid << endl << flush;
0099     }
0100 
0101     fcpu1 = fcpui;
0102     time1 = timei;
0103 
0104   }
0105 
0106   // Interface to the system time information.
0107   double fclock() {
0108     struct tms tmsbuf;
0109     times(&tmsbuf);
0110     double d =
0111       tmsbuf.tms_utime+tmsbuf.tms_stime+tmsbuf.tms_cutime+tmsbuf.tms_cstime;
0112     d /= sysconf(_SC_CLK_TCK);
0113     return d;
0114   }
0115 
0116   // Check if this is a good time to print out a status line.
0117   bool statusTime(long i, long n) const {
0118     if ( i <= 0 ) return false;
0119     if ( i == n ) return true;
0120     if ( i > n/2 ) i = n-i;
0121     while ( i >= 10 && !(i%10) ) i /= 10;
0122     if ( i == 1 || i == 2 || i == 5 ) return true;
0123     if ( secstep > 0 && time(0) > time1 + secstep ) return true;
0124     return false;
0125   }
0126 
0127   // Initialise the basic engine.
0128   void init(long n) {
0129     N = n;
0130     count = 0;
0131     fcpu0 = fcpu1 = fclock();
0132     time0 = time1 = time(0);
0133     char name[1024];
0134     gethostname(name,1024);
0135     host = name;
0136     if ( host.find(".") != string::npos )
0137       host = host.substr(0, host.find("."));
0138     pid = getpid();
0139     char date[1024];
0140     strftime(date,1024,"%y.%m.%d %H:%M",localtime(&time0));
0141     ostream & os = cout;
0142     os << date << "        0/" << setw(9);
0143     os.setf(ios::left, ios::adjustfield);
0144     os << n;
0145     os.setf(ios::right, ios::adjustfield);
0146     os << " Initializing...                "
0147        << host << ":" << pid << endl << flush;
0148   }
0149 
0150 private:
0151 
0152   // If larger than 0, a status line will be written every secstep
0153   // second.
0154   int secstep;
0155 
0156   // The clock when the run was started.
0157   time_t time0;
0158 
0159   // The cpu clock when the run was started.
0160   double fcpu0;
0161 
0162   // The clock the last time a status line was written out.
0163   time_t time1;
0164 
0165   // The cpu clock the last time a status line was written out.
0166   double fcpu1;
0167 
0168   // The host on which we are running.
0169   string host;
0170 
0171   // The pid of the current process.
0172   pid_t pid;
0173 
0174   // The number of iterations
0175   long N;
0176 
0177   // The number of iterations so far
0178   long count;
0179 
0180 };
0181 
0182 }
0183 
0184 #endif