Jpp
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
JEventTimesliceWriter.cc
Go to the documentation of this file.
1 #include <string>
2 #include <iostream>
3 #include <fstream>
4 
5 #include "TRandom3.h"
6 
7 #include "evt/Head.hh"
8 #include "evt/Evt.hh"
9 #include "evt/Hit.hh"
10 
11 #include "JAAnet/JAAnetToolkit.hh"
12 #include "JAAnet/JEvtEvaluator.hh"
13 
15 #include "JDetector/JDetector.hh"
21 
22 
25 
27 #include "JSupport/JMeta.hh"
30 #include "JSupport/JSupport.hh"
31 #include "JSupport/JTreeScanner.hh"
33 
34 #include "Jeep/JParser.hh"
35 #include "Jeep/JMessage.hh"
36 
37 
38 /**
39  * \file
40  * Auxiliary program to convert multiple Monte Carlo events to DAQ timeslices.
41  * Events are timed according to a given rate (if > 0), otherwise they are timed according to Evt::mc_t.
42  * \author mdejong, mlincett
43  */
44 int main(int argc, char **argv)
45 {
46  using namespace std;
47  using namespace JPP;
48  using namespace KM3NETDAQ;
49 
50 
51  JMultipleFileScanner<JAAnetTypes_t> inputFile;
52  JFileRecorder <JTYPELIST<JAAnetTypes_t, JDAQTimeslice, JMeta, JRootTypes_t>::typelist> outputFile;
53  JLimit_t& numberOfEvents = inputFile.getLimit();
54  string detectorFile;
55  int run;
56  JPMTParametersMap pmtParameters;
57  JK40Rates rates_Hz;
58  double eventRate_Hz;
59  UInt_t seed;
60  int debug;
61 
62  try {
63 
64  JParser<> zap("Auxiliary program to convert multiple Monte Carlo events to time slices.");
65 
66  zap['f'] = make_field(inputFile);
67  zap['o'] = make_field(outputFile) = "timeslice.root";
68  zap['n'] = make_field(numberOfEvents) = JLimit::max();
69  zap['a'] = make_field(detectorFile);
70  zap['R'] = make_field(run) = 1;
71  zap['P'] = make_field(pmtParameters) = JPARSER::initialised();
72  zap['B'] = make_field(rates_Hz) = JPARSER::initialised();
73  zap['r'] = make_field(eventRate_Hz);
74  zap['S'] = make_field(seed) = 0;
75  zap['d'] = make_field(debug) = 0;
76 
77  zap(argc, argv);
78  }
79  catch(const exception &error) {
80  FATAL(error.what() << endl);
81  }
82 
83  gRandom->SetSeed(seed);
84 
85  cout.tie(&cerr);
86 
88 
89  if (pmtParameters.getQE() != 1.0) {
90 
91  WARNING("Correct background rates with global efficiency " << pmtParameters.getQE() << endl);
92 
93  rates_Hz.correct(pmtParameters.getQE());
94  }
95 
96  // parameters
97 
98  DEBUG("PMT paramaters: " << endl << pmtParameters << endl);
99  DEBUG("K40 rates: " << endl << rates_Hz << endl);
100 
101  if (eventRate_Hz < 0.0) {
102  FATAL("Invalid event rate " << eventRate_Hz << "; consider using JRandomTimesliceWriter." << endl);
103  }
104 
105  // detector
106 
107  JDetector detector;
108 
109  try {
110  load(detectorFile, detector);
111  }
112  catch(const JException& error) {
113  FATAL(error);
114  }
115 
116  // header
117 
118  Head header;
119 
120  try {
121  header = getHeader(inputFile);
122  }
123  catch (const JLANG::JNullPointerException error) {
124  FATAL("MC header is invalid");
125  }
126 
127  double liveTimeMC = JHead(header).livetime.numberOfSeconds;
128 
129  if (liveTimeMC < 0) {
130  FATAL("MC live time is negative; input file may be corrupted.");
131  }
132 
133  // background simulator
134 
135  JPMTParametersMap::Throw(false);
136 
137  JDetectorSimulator simbad(detector);
138 
139  simbad.reset(new JPMTDefaultSimulator(pmtParameters, detector));
140  simbad.reset(new JK40DefaultSimulator(rates_Hz));
141  simbad.reset(new JCLBDefaultSimulator());
142 
143  // output file
144 
145  outputFile.open();
146 
147  if (!outputFile.is_open()) FATAL("Error opening file " << outputFile << endl);
148 
149  outputFile.put(*gRandom);
150  outputFile.put(JMeta(argc, argv));
151  outputFile.put(header);
152 
153  // input stream;
154 
155  bool absTime = false;
156 
157  JTreeScannerInterface<Evt>* scan;
158 
159  if (eventRate_Hz == 0.0 && liveTimeMC == 0.0) {
160 
161  NOTICE("Event will be timed according to absolute MC time." << endl);
162 
163  absTime = true;
164 
165  // sorted access;
166  scan = new JTreeScanner<Evt, JEvtEvaluator>(inputFile);
168 
169  } else {
170 
171  // unsorted access;
172  scan = new JTreeScanner<Evt>(inputFile);
174 
175  if (eventRate_Hz == 0.0 && liveTimeMC > 0.0) {
176  int nEntries = scan->getEntries();
177  eventRate_Hz = nEntries / liveTimeMC;
178  DEBUG(nEntries << " events to be written." << endl);
179  NOTICE("MC live time is " << liveTimeMC << " s" << endl);
180  NOTICE("Event rate set to " << eventRate_Hz << " Hz from MC header." << endl);
181  }
182  }
183 
184  // begin timeslice generation;
185 
186  // state variables;
187  bool pendingEvt = false;
188  bool pendingTimeslice = false;
189 
190  Evt* event = NULL; // pending event;
191 
192  JTimeRange timeRange;
193  double tDAQ = 0; // DAQ event time;
194  double tOff = 0; // hit production time offset;
195 
196  int frame_index = 0;
197  JDAQChronometer chronometer;
198  JRandomTimeslice timeslice;
199 
200  counter_type evtCount = 0;
201 
202  while (pendingEvt || scan->hasNext()) {
203 
204  if (!pendingTimeslice) {
205  // update background timeslice;
206  frame_index++;
207  chronometer = JDAQChronometer(detector.getID(), run, frame_index, JDAQUTCExtended(getTimeOfFrame(frame_index)));
208  timeslice = JRandomTimeslice(chronometer, simbad);
209  DEBUG("evt count: " << setw(10) << evtCount << endl);
210  STATUS("frame index: " << setw(10) << frame_index << " | evt count: " << setw(10) << evtCount << "\r"); DEBUG(endl);
211  pendingTimeslice = true;
212  }
213 
214  if (!pendingEvt) {
215  // get new event;
216  event = scan->next();
217  timeRange = getTimeRange(*event);
218  tOff = timeRange.is_valid() ? timeRange.getLowerLimit() : 0;
219  // update DAQ time according to absolute or random;
220  if (absTime)
221  tDAQ = getEvtValue(*event) + tOff;
222  else
223  tDAQ += gRandom->Exp(1.0e9 / eventRate_Hz);
224 
225  DEBUG("event time [s] " << setprecision(5) << tDAQ * 1.0e-9 << endl);
226  pendingEvt = true;
227  }
228 
229  // DEBUG("tDAQ : " << tDAQ << " - frame index: " << frame_index << " - DAQ frame index " << getFrameIndex(tDAQ) << endl);
230  if (getFrameIndex(tDAQ) == frame_index) {
231 
232  // process event;
233  if (timeRange.is_valid()) {
234  DEBUG(*event << endl);
235  // real start time of the hits will be always tDAQ;
236  event->mc_t = tDAQ - tOff;
237  timeslice.add(JEventTimeslice(chronometer, simbad, *event));
238  evtCount++;
239  }
240  // event processed;
241  outputFile.put(*event);
242  pendingEvt = false;
243  } else {
244  // event time is past end of timeslice;
245  DEBUG(timeslice << endl);
246  outputFile.put(timeslice);
247  pendingTimeslice = false;
248  }
249 
250  }
251 
252  if (pendingTimeslice) {
253  DEBUG(timeslice << endl);
254  outputFile.put(timeslice);
255  pendingTimeslice = false;
256  }
257 
258  STATUS(endl);
259 
260  outputFile.put(*gRandom);
261  outputFile.close();
262 
263  NOTICE(evtCount << " events written over " << frame_index << " timeslices. " << endl);
264 }
Auxiliary class for ROOT I/O of application specific meta data.
Definition: JMeta.hh:71
Timeslice with random data.
Utility class to parse command line options.
Definition: JParser.hh:1410
#define WARNING(A)
Definition: JMessage.hh:63
debug
Definition: JMessage.hh:27
Timeslice with Monte Carlo event.
#define STATUS(A)
Definition: JMessage.hh:61
Recording of objects on file according a format that follows from the file name extension.
Structure to store the ToT mean and standard deviation of the hits produced by a nanobeacon in a sour...
Empty structure for specification of parser element that is initialised (i.e.
Definition: JParser.hh:64
Long64_t counter_type
Type definition for counter.
Definition: JCounter.hh:24
string outputFile
Data structure for UTC time.
Data structure for detector geometry and calibration.
double getTimeOfFrame(const int frame_index)
Get start time of frame in ns since start of run for a given frame index.
Definition: JDAQClock.hh:185
JRange< double > JTimeRange
Type definition for time range.
JTimeRange getTimeRange(const Evt &event)
Get time range (i.e.
Head getHeader(const JMultipleFileScanner_t &file_list)
Get Monte Carlo header.
JLimit JLimit_t
Type definition of limit.
Definition: JLimit.hh:214
void setDAQLongprint(const bool option)
Set DAQ print option.
Definition: JDAQPrint.hh:28
Exception for null pointer operation.
Definition: JException.hh:198
static const JEvtEvaluator getEvtValue
Function object for evaluation of DAQ objects.
JAANET::livetime livetime
Definition: JHead.hh:868
int getFrameIndex(const double t_ns)
Get frame index for a given time in ns.
Definition: JDAQClock.hh:251
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
Definition: JParser.hh:1836
ROOT I/O of application specific meta data.
Definition of hit and track types and auxiliary methods for handling Monte Carlo data.
#define NOTICE(A)
Definition: JMessage.hh:62
void load(const JString &file_name, JDetector &detector)
Load detector from input file.
int debug
debug level
Definition: JSirene.cc:59
General purpose messaging.
Monte Carlo run header.
Definition: JHead.hh:727
#define FATAL(A)
Definition: JMessage.hh:65
Scanning of objects from multiple files according a format that follows from the extension of each fi...
Utility class to parse command line options.
ROOT TTree parameter settings.
const JLimit & getLimit() const
Get limit.
Definition: JLimit.hh:72
double numberOfSeconds
Live time [s].
Definition: JHead.hh:588
#define DEBUG(A)
Message macros.
Definition: JMessage.hh:60
int main(int argc, char *argv[])
Definition: Main.cpp:15