Jpp  17.1.1
the software that should make you happy
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Functions
JDataQuality.cc File Reference

Main program to evaluate quality data from data base. More...

#include <iostream>
#include <sstream>
#include <fstream>
#include <iomanip>
#include <vector>
#include <set>
#include <map>
#include "TROOT.h"
#include "TFile.h"
#include "TH1D.h"
#include "TF1.h"
#include "TString.h"
#include "TNtuple.h"
#include "TRegexp.h"
#include "JDB/JDB.hh"
#include "JDB/JSelector.hh"
#include "JDB/JSelectorSupportkit.hh"
#include "JDB/JRunQuality.hh"
#include "JDB/JRunsetups.hh"
#include "JDB/JDBToolkit.hh"
#include "JLang/JLangToolkit.hh"
#include "JTools/JRange.hh"
#include "JROOT/JRootClass.hh"
#include "JROOT/JRootPrinter.hh"
#include "JROOT/JRootToolkit.hh"
#include "JROOT/JRootStreamObjectOutput.hh"
#include "JROOT/JRootDictionary.hh"
#include "JROOT/JASCIIFileStreamer.hh"
#include "JROOT/JManager.hh"
#include "JSupport/JMeta.hh"
#include "JSupport/JFilenameSupportkit.hh"
#include "JDataQuality/JGITTags.hh"
#include "Jeep/JeepToolkit.hh"
#include "Jeep/JComment.hh"
#include "Jeep/JParser.hh"
#include "Jeep/JMessage.hh"

Go to the source code of this file.

Functions

int main (int argc, char **argv)
 

Detailed Description

Main program to evaluate quality data from data base.

The evaluation of the data quality is based on the following procedure.
For each data taking run, the script JQAQC.sh is executed which produces a set of values. The values are subsequently uploaded into the database in table "runsummarynumbers". This table is a general purpose table for any value related to some data taking run. With this application, the QA/QC data are consistently downloaded from the database; evaluated according some formula and tested against a validity range. The underlying data structure is JDATABASE::JRunQuality.

The formula and validity range are referred to as a condition and can be specified with option -Q. Each condition has an optional weight (default is 1). The normalised total weight is used to define an overall quality, ranging from 0 = worst to 1 = best. There is also the possibility to specify a veto (option -V), which is similar to a condition but only the number of vetoes is counted. The overall quality and the number of vetoes can be used to accept or reject a data taking run.

By default, a list of the run numbers, the overall weight and the number of vetoes is printed. If a ROOT file is specified for the output (i.e. filename extension is JSUPPORT::ROOT_FILE_FORMAT), a file is written which contains a histogram for each condition and each veto; some summary histograms and a ROOT n-tuple. If an ASCII file is specified for the output (i.e. filename extension is JSUPPORT::ASCII_FILE_FORMAT), a text file is written which can subsequently be used as input file.

Author
mdejong

Definition in file JDataQuality.cc.

Function Documentation

int main ( int  argc,
char **  argv 
)

Definition at line 127 of file JDataQuality.cc.

128 {
129  using namespace std;
130  using namespace JPP;
131 
132  typedef JRange<int> JRange_t;
133  typedef vector<JCondition> JCondition_t;
134 
135  JServer server;
136  string usr;
137  string pwd;
138  string cookie;
139  string inputFile;
140  string outputFile;
141  string detid;
142  JRange_t runs;
143  vector<string> source;
144  JCondition_t condition;
145  JCondition_t veto;
146  TRegexp regexp(".");
147  JSelector selection;
148  int debug;
149 
150  try {
151 
152  JParser<> zap("Main program to evaluate quality data from data base."\
153  "\nThe condition and veto can be any TFormula compatible expression involving QA/QC parameters (see e.g. JQAQC.sh -h).");
154 
155  zap['s'] = make_field(server) = getServernames();
156  zap['u'] = make_field(usr) = "";
157  zap['!'] = make_field(pwd) = "";
158  zap['C'] = make_field(cookie) = "";
159  zap['f'] = make_field(inputFile, "Optional input file instead of database.") = "";
160  zap['o'] = make_field(outputFile, "ROOT file with histograms and n-tuple or ASCII file with QA/QC data.") = "quality.root";
161  zap['D'] = make_field(detid) = "";
162  zap['R'] = make_field(runs, "Run range") = JRange_t(1, JRange_t::getMaximum());
163  zap['S'] = make_field(source, "GIT versions") = getGITTags(TRegexp("v[0-9]*\\.[0-9]*\\.[0-9]*$"), JGITTags_t::key_type("2019-04-12"));
164  zap['Q'] = make_field(condition, "User defined conditions") = JPARSER::initialised();
165  zap['V'] = make_field(veto, "User defined vetos.") = JPARSER::initialised();
166  zap['r'] = make_field(regexp, "TRegexp for selection of run setup names.") = JPARSER::initialised();
167  zap['@'] = make_field(selection) = JPARSER::initialised();
168  zap['d'] = make_field(debug, "Debug level") = 1;
169 
170  zap(argc, argv);
171  }
172  catch(const exception &error) {
173  FATAL(error.what() << endl);
174  }
175 
176 
177  double W = 0.0;
178 
179  for (JCondition_t::const_iterator i = condition.begin(); i != condition.end(); ++i) {
180  W += i->weight;
181  }
182 
184  if (W <= 0.0) {
185  FATAL("Invalid total weight: " << W << endl);
186  }
187  }
188 
189 
190  JRunsetups setups; // run -> value
191  set<JRunQuality> buffer; // storage
192 
193 
194  if (inputFile == "") { // read data from database
195 
196  ASSERT(detid != "");
197 
198  try {
199 
200  JDB::reset(usr, pwd, cookie);
201 
202  const int ID = getDetector<int> (detid);
203  detid = getDetector<string>(detid);
204 
205  // run setups
206 
207  selection += getSelector<JRuns>(ID);
208 
209  NOTICE("Extracting run information from database... " << flush);
210 
211  ResultSet& rs = getResultSet(getTable<JRuns>(), selection);
212 
213  for (JRuns parameters; rs >> parameters; ) {
214  if (TString(parameters.RUNSETUPNAME.c_str()).Contains(regexp)) {
215  setups.put(parameters);
216  }
217  }
218 
219  rs.Close();
220 
221  NOTICE("OK" << endl);
222 
223  // run summary data
224 
225  for (vector<string>::const_iterator git = source.begin(); git != source.end(); ++git) {
226 
227  typedef map<string, string> data_type;
228  typedef map<int, data_type> map_type;
229 
230  map_type zmap;
231 
232  JSelector selector = getSelector<JRunSummaryNumbers>(detid, runs.getLowerLimit(), runs.getUpperLimit());
233 
234  selector.add(&JRunSummaryNumbers::SOURCE_NAME, *git);
235 
236  try {
237 
238  NOTICE("Extracting run summmary information with source " << *git << " from database... " << flush);
239 
240  ResultSet& rs = getResultSet(getTable<JRunSummaryNumbers>(), selector);
241 
242  for (JRunSummaryNumbers parameters; rs >> parameters; ) {
243  if (setups.has(parameters.RUN)) {
244  zmap[parameters.RUN].insert(make_pair(parameters.PARAMETER_NAME, parameters.DATA_VALUE));
245  }
246  }
247 
248  rs.Close();
249 
250  NOTICE("OK" << endl);
251  }
252  catch(const exception& error) { NOTICE(endl); }
253 
254  for (map_type::const_iterator run = zmap.begin(); run != zmap.end(); ++run) {
255 
256  JRunQuality quality;
257 
258  quality.GIT = *git;
259  quality.detector = ID;
260  quality.run = run->first;
261  quality.name = setups[run->first].name;
262  quality.value = setups[run->first].value;
263 
264  for (data_type::const_iterator i = run->second.begin(); i != run->second.end(); ++i) {
265  quality.put(i->first, i->second);
266  }
267 
268  quality.name = replace(quality.name, ' ', '_');
269 
270  buffer.insert(quality); // only insert if absent
271  }
272  }
273  }
274  catch(const exception& error) {
275  FATAL(error.what() << endl);
276  }
277 
278  } else { // read data from file
279 
280  JASCIIFileReader<JRunQuality> in(inputFile.c_str(), JDBDictionary::getInstance());
281 
282  JComment comment;
283 
284  in >> comment;
285 
286  for (JRunQuality quality; in >> quality; ) {
287  buffer.insert(quality);
288  }
289 
290  in.close();
291  }
292 
293 
294  if (buffer.empty()) {
295  FATAL("No data." << endl);
296  }
297 
298 
300 
301  runs = JRange_t(buffer.begin()->run, buffer.rbegin()->run);
302 
303  TH1D h0("h0", NULL, 1000, 0.0, 1.01);
304  TH1D h1("h1", NULL, condition.size(), -0.5, condition.size() - 0.5);
305 
306  for (size_t i = 0; i != condition.size(); ++i) {
307  h1.GetXaxis()->SetBinLabel(i+1, condition[i].formula.c_str());
308  }
309 
310  h0.SetMinimum(0.0);
311  h0.SetMaximum(1.1 * (runs.getUpperLimit() - runs.getLowerLimit()));
312 
313  h1.SetMinimum(0.0);
314  h1.SetMaximum(1.1 * (runs.getUpperLimit() - runs.getLowerLimit()));
315 
316  const Double_t xmin = runs.getLowerLimit() - 0.5;
317  const Double_t xmax = runs.getUpperLimit() + 0.5;
318 
319  JManager<TString, TH1D> H1(new TH1D("%", NULL, runs.getLength() + 1, xmin, xmax));
320 
321  // show validity range
322 
323  for (JCondition_t::const_iterator i = condition.begin(); i != condition.end();++i) {
324  H1[i->formula]->GetListOfFunctions()->Add(new TF1(MAKE_CSTRING("C " << i->formula << ":upper"), MAKE_CSTRING(i->range.getUpperLimit()), xmin, xmax));
325  H1[i->formula]->GetListOfFunctions()->Add(new TF1(MAKE_CSTRING("C " << i->formula << ":lower"), MAKE_CSTRING(i->range.getLowerLimit()), xmin, xmax));
326  }
327 
328  for (JCondition_t::const_iterator i = veto.begin(); i != veto.end();++i) {
329  H1[i->formula]->GetListOfFunctions()->Add(new TF1(MAKE_CSTRING("V " << i->formula << ":upper"), MAKE_CSTRING(i->range.getUpperLimit()), xmin, xmax));
330  H1[i->formula]->GetListOfFunctions()->Add(new TF1(MAKE_CSTRING("V " << i->formula << ":lower"), MAKE_CSTRING(i->range.getLowerLimit()), xmin, xmax));
331  }
332 
333  ostringstream os; // N-tuple format
334 
335  os << "run";
336 
337  for (size_t i = 0; i != condition.size(); ++i) {
338  os << ":" << (char) ('a' + i);
339  }
340 
341  os << ":Q:V:R";
342 
343  TNtuple n1("n1", "quality", os.str().c_str());
344 
345 
346  // process data
347 
348  for (set<JRunQuality>::const_iterator quality = buffer.begin(); quality != buffer.end(); ++quality) {
349 
350  vector<Float_t> tuple(1, (Float_t) quality->run);
351 
352  double w = 0.0;
353 
354  for (size_t i = 0; i != condition.size(); ++i) {
355 
356  const JCondition& ps = condition[i];
357  const double y = getResult(ps.formula, *quality);
358 
359  DEBUG(ps.formula << ' ' << y << endl);
360 
361  tuple.push_back((Float_t) y);
362 
363  TH1D* p = H1[ps.formula];
364 
365  p->SetBinContent(p->FindBin((double) quality->run), y);
366  p->SetBinError (p->FindBin((double) quality->run), numeric_limits<double>::epsilon());
367 
368  if (ps.range(y)) {
369  w += ps.weight;
370  }
371 
372  h1.AddBinContent(i + 1, ps.range(y) ? 1.0 : 0.0);
373  }
374 
375  const double Q = w/W;
376 
377  tuple.push_back((Float_t) Q);
378 
379  int V = 0;
380 
381  for (size_t i = 0; i != veto.size(); ++i) {
382 
383  const JCondition& ps = veto[i];
384  const double y = getResult(ps.formula, *quality);
385 
386  DEBUG(ps.formula << ' ' << y << endl);
387 
388  TH1D* p = NULL;
389 
390  p = H1[ps.formula];
391 
392  p->SetBinContent(p->FindBin((double) quality->run), y);
393  p->SetBinError (p->FindBin((double) quality->run), numeric_limits<double>::epsilon());
394 
395  p = H1[MAKE_STRING("VETO[" << ps.formula << "]")];
396 
397  p->SetBinContent(p->FindBin((double) quality->run), ps.range(y) ? 0.0 : 1.0);
398  p->SetBinError (p->FindBin((double) quality->run), numeric_limits<double>::epsilon());
399 
400  if (!ps.range(y)) {
401  ++V;
402  }
403  }
404 
405  tuple.push_back((Float_t) V);
406  tuple.push_back((Float_t) setups.get(quality->run));
407 
408  h0.Fill(Q);
409  n1.Fill(tuple.data());
410 
411  cout << setw(8) << quality->run << ' ' << FIXED(5,3) << Q << ' ' << setw(2) << V << endl;
412  }
413 
414  double w = 0.0;
415 
416  for (Int_t i = 0; i <= h0.GetXaxis()->GetNbins(); ++i) {
417  h0.SetBinContent(i, (w += h0.GetBinContent(i)));
418  }
419 
420  // store results
421 
422  TFile out(outputFile.c_str(), "recreate");
423 
424  out << h0 << h1 << n1 << H1;
425 
426  out.Write();
427  out.Close();
428  }
429 
430 
432 
433  // store data
434 
435  JASCIIFileWriter<JRunQuality> out(outputFile.c_str(), JDBDictionary::getInstance());
436 
437  out.setf(ios::fixed);
438 
439  JComment comment;
440 
441  comment.add(JMeta(argc, argv));
442 
443  out << comment;
444 
445  for (set<JRunQuality>::const_iterator i = buffer.begin(); i != buffer.end(); ++i) {
446  out << *i << endl;
447  }
448 
449  out.close();
450  }
451 }
const double xmax
Definition: JQuadrature.cc:24
Utility class to parse command line options.
Definition: JParser.hh:1517
data_type w[N+1][M+1]
Definition: JPolint.hh:778
Q(UTCMax_s-UTCMin_s)-livetime_s
TString replace(const TString &target, const TRegexp &regexp, const T &replacement)
Replace regular expression in input by given replacement.
Definition: JPrintResult.cc:63
std::vector< std::string > getGITTags(const TRegexp &regexp, const JGITTags_t::key_type &date)
Get selection of GIT tags.
*fatal Wrong number of arguments esac JCookie sh typeset Z DETECTOR typeset Z SOURCE_RUN typeset Z TARGET_RUN set_variable PARAMETERS_FILE $WORKDIR parameters
Definition: diff-Tuna.sh:38
#define MAKE_CSTRING(A)
Make C-string.
Definition: JPrint.hh:136
Empty structure for specification of parser element that is initialised (i.e. does not require input)...
Definition: JParser.hh:83
Auxiliary data structure for floating point format specification.
Definition: JManip.hh:446
static const char *const ASCII_FILE_FORMAT
file name extension ASCII format
V(JDAQEvent-JTriggerReprocessor)*1.0/(JDAQEvent+1.0e-10)
string outputFile
#define MAKE_STRING(A)
Make string.
Definition: JPrint.hh:127
#define ASSERT(A,...)
Assert macro.
Definition: JMessage.hh:90
T & getInstance(const T &object)
Get static instance from temporary object.
Definition: JObject.hh:75
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
Definition: JParser.hh:1993
Double_t getResult(const TString &text, TObject *object=NULL)
Get result of given textual formula.
#define NOTICE(A)
Definition: JMessage.hh:64
then echo Variable JPP_DIR undefined exit fi source $JPP_DIR setenv sh $JPP_DIR &dev null set_variable DETECTOR $JPP_DATA km3net_reference detx set_variable NUMBER_OF_STRINGS set_variable ID if do_usage *then usage $script[detector file[variant[identifier]]] fi case set_variable ID
Definition: JDetector.sh:24
#define FATAL(A)
Definition: JMessage.hh:67
void reset(T &value)
Reset value.
const double xmin
Definition: JQuadrature.cc:23
std::string getFilenameExtension(const std::string &file_name)
Get file name extension, i.e. part after last JEEP::FILENAME_SEPARATOR if any.
Definition: JeepToolkit.hh:109
ResultSet & getResultSet(const std::string &query)
Get result set.
Definition: JDB.hh:432
std::vector< JServer > getServernames()
Get list of names of available database servers.
Definition: JDB.hh:98
then fatal Wrong number of arguments fi set_variable DETECTOR $argv[1] set_variable INPUT_FILE $argv[2] eval JPrintDetector a $DETECTOR O IDENTIFIER eval JPrintDetector a $DETECTOR O SUMMARY JAcoustics sh $DETECTOR_ID source JAcousticsToolkit sh CHECK_EXIT_CODE typeset A EMITTERS get_tripods $WORKDIR tripod txt EMITTERS get_transmitters $WORKDIR transmitter txt EMITTERS for EMITTER in
Definition: JCanberra.sh:46
static const char *const ROOT_FILE_FORMAT
file name extension ROOT format
const double epsilon
Definition: JQuadrature.cc:21
int debug
debug level
#define DEBUG(A)
Message macros.
Definition: JMessage.hh:62