NAIA  1.0.2
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups
OnDemandContainer.h
Go to the documentation of this file.
1 
7 #include "TTree.h"
8 
9 #include <iostream>
10 #include <limits>
11 
12 #ifndef NAIA_OnDemandContainer_h
13 #define NAIA_OnDemandContainer_h
14 
15 namespace NAIA {
16 
44 template <class T> class OnDemandContainer {
45 public:
46  OnDemandContainer() = default;
47 
54  void LoadEvent() {
55  if (!m_cacheIsValid && m_ioEnabled) {
56  m_branch->GetEntry(m_treeEntry);
57  m_cacheIsValid = true;
58  }
59  // std::cout << m_branch << " thisEntry: " << m_branch->GetReadEntry()
60  // << " motherEntry: " << m_branch->GetMother()->GetReadEntry() << '\n';
61  }
62 
68  void SetTreeEntry(unsigned long long treeEntry) {
69  if (treeEntry == m_treeEntry)
70  return;
71  m_treeEntry = treeEntry;
72  m_cacheIsValid = false;
73  }
74 
80  void Branch(TTree *tree) {
81  if (m_ioEnabled)
82  tree->Branch(T::BranchName.c_str(), static_cast<T *>(this));
83  }
84 
91  void MirrorBranch(TTree *targetTree, const T *sourceContainer) {
92  // I'd like to avoid const_cast but TTree::Branch doesn't support const T* as a type
93  // for the input buffer
94  if (m_ioEnabled)
95  targetTree->Branch(T::BranchName.c_str(), const_cast<T *>(sourceContainer));
96  }
97 
103  void SetBranchAddress(TTree *tree) {
104  // ROOT needs the address of the pointer to the buffer object.
105  myPtrAddress = static_cast<T *>(this);
106  tree->SetBranchAddress(T::BranchName.c_str(), &myPtrAddress);
107  m_branch = tree->GetBranch(T::BranchName.c_str());
108  if (!m_branch)
109  m_ioEnabled = false;
110  }
111 
116  void DisableIO() const { m_ioEnabled = false; }
117 
127  T *operator->() {
128  if (!m_ioEnabled) {
129  throw std::runtime_error(T::BranchName + ": this container is not available on file");
130  }
131  LoadEvent();
132 
133  // VERY IMPORTANT: don't use "this" here, it will point to the "previous" event
134  return myPtrAddress;
135  }
136 
137 private:
139  TBranch *m_branch = nullptr;
140  unsigned long long m_treeEntry = std::numeric_limits<unsigned long long>::max();
141 
142  mutable bool m_cacheIsValid = false;
143  mutable bool m_ioEnabled = true;
144 };
145 } // namespace NAIA
146 #endif
void Branch(TTree *tree)
Create the TBranch associated with this container.
Mixin class to add &quot;read-on-demand&quot; behavior to an existing container class.
void SetTreeEntry(unsigned long long treeEntry)
Set the TTree entry number.
T * operator->()
Access operator. Use this to access container data
void SetBranchAddress(TTree *tree)
Setup reading of the data container.
void DisableIO() const
Disables I/O for this container. It won&#39;t be written on disk and trying to read it will cause an exce...
void LoadEvent()
Wrapper to call GetEntry on the underlying TBranch.
void MirrorBranch(TTree *targetTree, const T *sourceContainer)
Create a TBranch associated with this container mirroring from an existing container.
unsigned long long m_treeEntry