Jpp  master_rocky-37-gf0c5bc59d
the software that should make you happy
JTreeScanner.hh
Go to the documentation of this file.
1 #ifndef __JSUPPORT__JTREESCANNER__
2 #define __JSUPPORT__JTREESCANNER__
3 
4 #include <vector>
5 #include <string>
6 #include <ostream>
7 #include <iomanip>
8 #include <algorithm>
9 
10 #include "JLang/JNullType.hh"
11 #include "JLang/JPointer.hh"
12 #include "JLang/JConversion.hh"
13 #include "JLang/JEquals.hh"
14 #include "JROOT/JChainReader.hh"
15 #include "JROOT/JCounter.hh"
16 #include "JROOT/JRootSupportkit.hh"
17 #include "Jeep/JMessage.hh"
21 
22 
23 /**
24  * \author mdejong
25  */
26 
27 namespace JSUPPORT {}
28 namespace JPP { using namespace JSUPPORT; }
29 
30 namespace JSUPPORT {
31 
32  using JLANG::JPointer;
33  using JLANG::JEquals;
34  using JLANG::JNullType;
36  using JROOT::JChainReader;
37  using JROOT::counter_type;
38  using JEEP::JMessage;
39 
40 
41  /**
42  * Pattern match for names of sub-branches that will not be read when ordering elements in a TTree.
43  */
44  static const char* const BRANCH_PATTERN = "vector";
45 
46 
47  /**
48  * Base class for JTreeScanner.
49  *
50  * Following ROOT memory management, a JChainReader object is created
51  * at construction and not deleted at destruction of this object.
52  */
53  template<class JClass_t>
55  public JPointer< JChainReader<JClass_t> >
56  {
57  public:
58  /**
59  * Destructor.
60  */
62  {
63  if (this->is_valid()) {
64  this->get()->Reset();
65  }
66  }
67 
68 
69  /**
70  * Get file list.
71  *
72  * \return list of file names
73  */
75  {
76  if (this->is_valid())
77  return JMultipleFileScanner_t(*this->get());
78  else
79  return JMultipleFileScanner_t();
80  }
81 
82 
83  /**
84  * Type conversion.
85  *
86  * \return file list
87  */
88  operator JMultipleFileScanner_t() const
89  {
90  return getFilelist();
91  }
92 
93 
94  protected:
95  /**
96  * Default constructor.
97  */
99  JPointer< JChainReader<JClass_t> >(new JChainReader<JClass_t>())
100  {
101  gErrorIgnoreLevel = kError;
102  }
103  };
104 
105 
106  /**
107  * Template definition for direct access of elements in ROOT TChain.
108  *
109  * The optional second template argument is used to the determine the value of an element
110  * which defines the apparent order the elements in the TChain.
111  * It also provides for the mechanism to find a corresponding entry in the TChain.
112  *
113  * This class implements the JSUPPORT::JTreeScannerInterface interface.
114  */
115  template<class JClass_t = JNullType, class JEvaluator_t = JNullType>
116  class JTreeScanner;
117 
118 
119  /**
120  * Auxiliary base class for reporting messages.
121  */
122  template<>
124  public JMessage< JTreeScanner<> >
125  {
126  public:
128  };
129 
130 
131  /**
132  * Specialiation of class JTreeScanner for unordered direct access of elements in ROOT TChain.
133  *
134  * The method JROOT::actionAtFileOpen is called at opening of the first file.
135  *
136  * The iteration of elements in the TChain will be in order of appearance.
137  */
138  template<class JDerived_t, class JBase_t>
139  class JTreeScanner<JAssertConversion<JDerived_t, JBase_t>, JNullType> :
140  public virtual JTreeScannerInterface<JBase_t>, // interface
141  public JTreeScanner_t<JDerived_t>, // data source
142  public JTreeScanner<>, // messaging
143  public JEquals< JTreeScanner<JAssertConversion<JDerived_t, JBase_t>, JNullType> >
144  {
145  public:
146 
147  typedef JBase_t data_type;
149 
151 
152 
153  /**
154  * Default constructor.
155  */
157  counter(0)
158  {}
159 
160 
161  /**
162  * Constructor.
163  *
164  * \param file_list file list
165  * \param limit limit
166  */
167  JTreeScanner(const JMultipleFileScanner_t& file_list, const JLimit& limit = JLimit()) :
168  counter(0)
169  {
170  this->configure(file_list, limit);
171  }
172 
173 
174  /**
175  * Copy constructor.
176  *
177  * \param input TTree scanner
178  */
180  {
181  this->configure(input, JLimit());
182  }
183 
184 
185  /**
186  * Check equality.
187  *
188  * \param object TTree scanner
189  * \return true if TTree scanners are equal; else false
190  */
191  bool equals(const JTreeScanner& object) const
192  {
193  return (this->getLimit() == object.getLimit() &&
194  this->getFilelist() == object.getFilelist());
195  }
196 
197 
198  /**
199  * Rewind.
200  */
201  virtual void rewind() override
202  {
203  counter = 0;
204  }
205 
206 
207  /**
208  * Check availability of next element.
209  *
210  * \return true if the iteration has more elements.
211  */
212  virtual bool hasNext() override
213  {
214  if (counter < this->getLowerLimit()) {
215  skip(this->getLowerLimit() - counter);
216  }
217 
218  return (counter < this->getEntries() &&
219  counter < this->getUpperLimit());
220  }
221 
222 
223  /**
224  * Get next element.
225  *
226  * \return pointer to element.
227  */
228  virtual const pointer_type& next() override
229  {
230  if (this->hasNext()) {
231 
232  this->get()->GetEvent(counter++);
233 
234  ps.reset(this->get()->getAddress());
235 
236  } else {
237 
238  ps.reset(NULL);
239  }
240 
241  return ps;
242  }
243 
244 
245  /**
246  * Skip items.
247  *
248  * \param ns number of items to skip
249  * \return number of items skipped
250  */
251  virtual skip_type skip(const skip_type ns) override
252  {
253  return JROOT::advance(counter, ns, this->getEntries());
254  }
255 
256 
257  /**
258  * Configure.
259  *
260  * \param file_list file list
261  * \param limit limit
262  */
263  virtual void configure(const JMultipleFileScanner_t& file_list, const JLimit& limit) override
264  {
265  using namespace JROOT;
266 
267  this->setLimit(limit);
268 
269  this->rewind();
270 
271  this->get()->Reset();
272 
273  for (JMultipleFileScanner<>::const_iterator i = file_list.begin(); i != file_list.end(); ++i) {
274 
275  TFile* file = TFile::Open(i->c_str());
276 
277  if (file != NULL) {
278 
279  if (file->GetListOfKeys()->Contains(this->get()->getTreeName())) {
280  this->get()->Add(i->c_str());
281  }
282 
283  delete file;
284  }
285  }
286 
287  this->getEntries(); // load TTree to set internal file
288 
289  actionAtFileOpen<JDerived_t>(this->get()->GetCurrentFile());
290  actionAtFileOpen<JBase_t> (this->get()->GetCurrentFile());
291  }
292 
293 
294  /**
295  * Get number of entries.
296  *
297  * \return number of entries
298  */
299  virtual Long64_t getEntries() const override
300  {
301  return this->get()->GetEntries();
302  }
303 
304 
305  /**
306  * Get entry at given index.
307  *
308  * \param index index
309  * \return pointer to object (may be NULL)
310  */
311  virtual data_type* getEntry(Long64_t index) override
312  {
313  if (index >= 0 && index < this->getEntries()) {
314 
315  this->get()->GetEvent(index);
316 
317  return this->get()->getAddress();
318  }
319 
320  return NULL;
321  }
322 
323 
324  /**
325  * Get internal counter.
326  *
327  * \return counter
328  */
329  virtual counter_type getCounter() const override
330  {
331  return counter;
332  }
333 
334 
335  /**
336  * Get actual class name.
337  *
338  * \return class name
339  */
340  virtual const char* getClassName() const override
341  {
342  return JDerived_t::Class_Name();
343  }
344 
345  protected:
347  private:
350  };
351 
352 
353  /**
354  * Specialiation of class JTreeScanner for unordered direct access of elements in ROOT TChain.
355  *
356  * The iteration of elements in the TChain will be in order of appearance.
357  */
358  template<class JClass_t>
359  class JTreeScanner<JClass_t, JNullType> :
360  public JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JNullType>
361  {
362  public:
363  /**
364  * Default constructor.
365  */
367  {}
368 
369 
370  /**
371  * Constructor.
372  *
373  * \param file_list file list
374  * \param limit limit
375  */
376  JTreeScanner(const JMultipleFileScanner_t& file_list, const JLimit& limit = JLimit()) :
377  JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JNullType>(file_list, limit)
378  {}
379 
380 
381  /**
382  * Copy constructor.
383  *
384  * \param input TTree scanner
385  */
386  JTreeScanner(const JTreeScanner& input) :
387  JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JNullType>(input)
388  {}
389  };
390 
391 
392  /**
393  * Specialisation of class JTreeScanner for ordered direct access of elements in ROOT TChain.
394  *
395  * The optional second template argument is used to the determine the value of an element.
396  * The elements in the TChain are then ordered according these values (from low to high).
397  * To this end, the evaluator class should provide for the following operator:
398  * <pre>
399  * value_type operator()(const JBase_t& element) const;
400  * </pre>
401  * where <tt>value_type</tt> should internally be defined and
402  * for which the operators <tt><</tt> and <tt>-</tt> should be provided.\n
403  * As a result, the iteration of elements in the TChain will then be in the specified order.
404  * It also provides for the mechanism to find a corresponding entry at O(log(n)) look up time.
405  */
406  template<class JDerived_t, class JBase_t, class JEvaluator_t>
407  class JTreeScanner<JAssertConversion<JDerived_t, JBase_t>, JEvaluator_t> :
408  public JTreeScannerInterface<JBase_t, JEvaluator_t>,
409  public JTreeScanner<JAssertConversion<JDerived_t, JBase_t>, JNullType>
410  {
411  public:
412 
413  typedef JBase_t data_type;
416 
420  using JTreeScanner<>::debug;
421 
422 
423  /**
424  * Default constructor.
425  */
427  JTreeScannerInterface<JBase_t, JEvaluator_t>()
428  {}
429 
430 
431  /**
432  * Constructor.
433  *
434  * \param file_list file list
435  * \param evaluator evaluator
436  */
438  const JEvaluator_t& evaluator = JEvaluator_t()) :
439  JTreeScannerInterface<JBase_t, JEvaluator_t>(evaluator)
440  {
441  this->configure(file_list);
442  }
443 
444 
445  /**
446  * Constructor.
447  *
448  * \param file_list file list
449  * \param limit limit
450  * \param evaluator evaluator
451  */
453  const JLimit& limit,
454  const JEvaluator_t& evaluator = JEvaluator_t()) :
455  JTreeScannerInterface<JBase_t, JEvaluator_t>(evaluator)
456  {
457  this->configure(file_list, limit);
458  }
459 
460 
461  /**
462  * Get next element.
463  *
464  * \return pointer to element.
465  */
466  virtual const pointer_type& next() override
467  {
468  if (this->hasNext()) {
469 
470  this->get()->GetEvent(queue[this->counter++].index);
471 
472  ps.reset(this->get()->getAddress());
473 
474  } else {
475 
476  ps.reset(NULL);
477  }
478 
479  return ps;
480  }
481 
482 
483  /**
484  * Configure.
485  *
486  * \param file_list file list
487  * \param limit limit
488  */
489  virtual void configure(const JMultipleFileScanner_t& file_list, const JLimit& limit) override
490  {
491  using namespace std;
492 
494 
495  setBranchStatus(this->get()->GetBranch(this->get()->getBranchName()), BRANCH_PATTERN, false);
496 
497  queue.resize(this->getEntries());
498 
499  typename queue_type::iterator out = queue.begin();
500 
501  for (Long64_t i = 0, n0 = 0; i != this->getEntries(); ++i, ++out) {
502 
503  const Long64_t n1 = (100 * (i + 1)) / this->getEntries();
504 
505  if (n1 > n0) {
506 
507  STATUS(left << setw(24) << this->get()->GetName() << right << ' ' << setw(3) << n1 << "%\r"); DEBUG(endl);
508 
509  n0 = n1;
510  }
511 
512  this->get()->GetEvent(i);
513 
514  const data_type* p = this->get()->getAddress();
515 
516  *out = JEntry_t(i, this->JTreeScannerInterface<JBase_t, JEvaluator_t>::getValue(*p));
517  }
518  STATUS(left << setw(24) << this->get()->GetName() << right << endl);
519 
520  this->get()->SetBranchStatus("*", 1);
521 
522  sort(queue.begin(), queue.end());
523  }
524 
525 
526  /**
527  * Get entry at given index.
528  *
529  * \param index index
530  * \return pointer to object (may be NULL)
531  */
532  virtual data_type* getEntry(Long64_t index) override
533  {
534  if (index >= 0 && index < (Long64_t) queue.size()) {
535 
536  this->get()->GetEvent(queue[index].index);
537 
538  return this->get()->getAddress();
539  }
540 
541  return NULL;
542  }
543 
544 
545  /**
546  * Find index of element that is closest in value to given value.
547  *
548  * A subsequent call to method getEntry() will point to the corresponding object.
549  *
550  * \param value value
551  * \return index (-1 in case of error)
552  */
553  virtual Long64_t find(const value_type value) const override
554  {
555  using namespace std;
556 
557  if (!queue.empty()) {
558 
559  typename queue_type::const_iterator p = lower_bound(queue.begin(), queue.end(), value);
560 
561  if (p == queue.end()) {
562 
563  return queue.size() - 1;
564 
565  } else if (p == queue.begin()) {
566 
567  return 0;
568 
569  } else {
570 
571  typename queue_type::const_iterator q = p--;
572 
573  if (value - p->value < q->value - value)
574  return distance(queue.begin(), p);
575  else
576  return distance(queue.begin(), q);
577  }
578  }
579 
580  return -1;
581  }
582 
583  protected:
584  /**
585  * Auxiliary data structure for sorting of objects in TChain.
586  */
587  struct JEntry_t {
588  /**
589  * Default constructor.
590  */
592  index(-1),
593  value()
594  {}
595 
596 
597  /**
598  * Constructor.
599  *
600  * \param index index
601  * \param value value
602  */
603  JEntry_t(const Long64_t index,
604  const value_type value) :
605  index(index),
606  value(value)
607  {}
608 
609 
610  /**
611  * Comparison between two TChain entries.
612  *
613  * \param first first entry
614  * \param second second entry
615  * \return true if first value less than second; else false
616  */
617  friend inline bool operator<(const JEntry_t& first, const JEntry_t& second)
618  {
619  return first.value < second.value;
620  }
621 
622 
623  /**
624  * Comparison between TChain entry and value.
625  *
626  * \param entry entry
627  * \param value value
628  * \return true if given entry has less value; else false
629  */
630  friend inline bool operator<(const JEntry_t& entry, const value_type value)
631  {
632  return entry.value < value;
633  }
634 
635 
636  Long64_t index; //!< index in TChain
637  value_type value; //!< corresponding value
638  };
639 
640 
641  /**
642  * Type definition of internal queue for ordering the elements in the TChain.
643  */
645 
646 
647  /**
648  * Set status of branch.
649  *
650  * Note that the status of the branch and all sub-branches with names including given pattern will recursively be set.
651  *
652  * \param branch pointer to branch
653  * \param pattern pattern
654  * \param status status
655  */
656  static void setBranchStatus(TBranch* branch, const char* pattern, const bool status)
657  {
658  using namespace std;
659 
660  if (branch != NULL) {
661 
662  TObjArray* array = branch->GetListOfBranches();
663 
664  for (Int_t i = 0; i != array->GetEntries(); ++i) {
665 
666  TBranch* p = (TBranch*) array->At(i);
667 
668  if (p != NULL && string(p->GetName()).find(pattern) != string::npos) {
669 
670  if (p->GetSplitLevel() == 0) {
671 
672  NOTICE("Set status of branch " << p->GetName() << " to " << status << endl);
673 
674  p->SetStatus(status);
675  }
676  } else {
677 
678  setBranchStatus(p, pattern, status);
679  }
680  }
681  }
682  }
683 
684 
686 
687  private:
689  };
690 
691 
692  /**
693  * Specialiation of class JTreeScanner for ordered direct access of elements in ROOT TChain.
694  */
695  template<class JClass_t, class JEvaluator_t>
696  class JTreeScanner :
697  public JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JEvaluator_t>
698  {
699  public:
700  /**
701  * Default constructor.
702  */
704  {}
705 
706 
707  /**
708  * Constructor.
709  *
710  * \param file_list file list
711  * \param evaluator evaluator
712  */
714  const JEvaluator_t& evaluator = JEvaluator_t()) :
715  JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JEvaluator_t>(file_list, evaluator)
716  {}
717 
718 
719  /**
720  * Constructor.
721  *
722  * \param file_list file list
723  * \param limit limit
724  * \param evaluator evaluator
725  */
727  const JLimit& limit,
728  const JEvaluator_t& evaluator = JEvaluator_t()) :
729  JTreeScanner<JAssertConversion<JClass_t, JClass_t>, JEvaluator_t>(file_list, limit, evaluator)
730  {}
731  };
732 }
733 
734 #endif
TChain reading for template data type.
std::ostream & rewind(std::ostream &out)
Rewind character.
Definition: JManip.hh:222
General purpose messaging.
#define DEBUG(A)
Message macros.
Definition: JMessage.hh:62
#define STATUS(A)
Definition: JMessage.hh:63
#define NOTICE(A)
Definition: JMessage.hh:64
int debug
debug level
Definition: JSirene.cc:69
Scanning of objects from multiple files according a format that follows from the extension of each fi...
Type definition for counter for ROOT TTree and auxiliary methods.
Data type dependent action methods for customised ROOT version management.
Scanning of objects from a single file according a format that follows from the extension of each fil...
std::vector< T >::difference_type distance(typename std::vector< T >::const_iterator first, typename PhysicsEvent::const_iterator< T > second)
Specialisation of STL distance.
bool is_valid() const
Check validity of pointer.
Auxialiary class to assert type conversion.
Definition: JConversion.hh:43
Template implementation of class that holds pointer to object(s).
Definition: JPointer.hh:24
virtual JClass_t * get() const override
Get pointer.
Definition: JPointer.hh:64
Auxiliary class for template TChain reading.
Definition: JChainReader.hh:28
General purpose class for object reading from a list of file names.
Auxiliary interface for direct access of elements in ROOT TChain.
std::vector< JEntry_t > queue_type
Type definition of internal queue for ordering the elements in the TChain.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JLimit &limit, const JEvaluator_t &evaluator=JEvaluator_t())
Constructor.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JEvaluator_t &evaluator=JEvaluator_t())
Constructor.
virtual data_type * getEntry(Long64_t index) override
Get entry at given index.
virtual const pointer_type & next() override
Get next element.
JTreeScannerInterface< JBase_t, JEvaluator_t >::value_type value_type
virtual Long64_t find(const value_type value) const override
Find index of element that is closest in value to given value.
static void setBranchStatus(TBranch *branch, const char *pattern, const bool status)
Set status of branch.
virtual void configure(const JMultipleFileScanner_t &file_list, const JLimit &limit) override
Configure.
JTreeScannerInterface< JBase_t, JEvaluator_t >::pointer_type pointer_type
virtual const char * getClassName() const override
Get actual class name.
virtual data_type * getEntry(Long64_t index) override
Get entry at given index.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JLimit &limit=JLimit())
Constructor.
bool equals(const JTreeScanner &object) const
Check equality.
virtual skip_type skip(const skip_type ns) override
Skip items.
virtual Long64_t getEntries() const override
Get number of entries.
virtual const pointer_type & next() override
Get next element.
virtual void configure(const JMultipleFileScanner_t &file_list, const JLimit &limit) override
Configure.
virtual bool hasNext() override
Check availability of next element.
virtual counter_type getCounter() const override
Get internal counter.
JTreeScanner(const JTreeScanner &input)
Copy constructor.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JLimit &limit=JLimit())
Constructor.
Base class for JTreeScanner.
Definition: JTreeScanner.hh:56
~JTreeScanner_t()
Destructor.
Definition: JTreeScanner.hh:61
JTreeScanner_t()
Default constructor.
Definition: JTreeScanner.hh:98
JMultipleFileScanner_t getFilelist() const
Get file list.
Definition: JTreeScanner.hh:74
Template definition for direct access of elements in ROOT TChain.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JLimit &limit, const JEvaluator_t &evaluator=JEvaluator_t())
Constructor.
JTreeScanner()
Default constructor.
JTreeScanner(const JMultipleFileScanner_t &file_list, const JEvaluator_t &evaluator=JEvaluator_t())
Constructor.
unsigned int skip_type
Type definition for number of objects to skip.
bool equals(const JFirst_t &first, const JSecond_t &second, const double precision=std::numeric_limits< double >::min())
Check equality.
Definition: JMathToolkit.hh:87
This name space includes all other name spaces (except KM3NETDAQ, KM3NET and ANTARES).
Auxiliary classes and methods for ROOT I/O.
counter_type advance(counter_type &counter, const counter_type value, const counter_type limit=std::numeric_limits< counter_type >::max())
Advance counter.
Long64_t counter_type
Type definition for counter.
std::vector< size_t > ns
Support classes and methods for experiment specific I/O.
Definition: JDataWriter.cc:38
static const char *const BRANCH_PATTERN
Pattern match for names of sub-branches that will not be read when ordering elements in a TTree.
Definition: JTreeScanner.hh:44
void configure(const T &value, const JAbstractCollection< JAbscissa_t > &bounds, JBool< false > option)
Configuration of value.
Definition: JSTDTypes.hh:14
Auxiliary class for handling debug parameter within a class.
Definition: JMessage.hh:44
Template definition of auxiliary base class for comparison of data structures.
Definition: JEquals.hh:84
Auxiliary class for no type definition.
Definition: JNullType.hh:19
Auxiliary class for defining the range of iterations of objects.
Definition: JLimit.hh:45
Auxiliary base class for list of file names.
friend bool operator<(const JEntry_t &entry, const value_type value)
Comparison between TChain entry and value.
friend bool operator<(const JEntry_t &first, const JEntry_t &second)
Comparison between two TChain entries.