ATLAS Offline Software
Loading...
Searching...
No Matches
xAODCutFlowHelpers.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
5
6// This functions header
8
9// STL includes
10#include <string>
11#include <vector>
12#include <cmath>
13
14// ROOT includes
15#include <TH1.h>
16
17// Local include(s):
19
20
21
24 const std::string& histName,
25 int minCycle, int maxCycle ) {
26 // Lets first make some checks
27 if (!cbkCont) return nullptr;
28
29 // Get the maximum cycle number that we need to worry about
30 const int cbkMaxCycle = cbkCont->maxCycle();
31 if (maxCycle<0) maxCycle = cbkMaxCycle;
32
33 // Now, find all xAOD::CutBookkeepers in the container that we care about
34 std::vector<const xAOD::CutBookkeeper*> cbks;
35 cbks.reserve(cbkCont->size());
36 for ( const xAOD::CutBookkeeper* cbk : *cbkCont ){
37 const int cycle = cbk->cycle();
38 if ( cycle >= minCycle && cycle <= maxCycle ){ cbks.push_back(cbk); }
39 }
40 const std::size_t nCBK = cbks.size();
41
42 // Create the histogram:
43 const std::string histTitle = histName + ", minCycle=" + std::to_string(minCycle)
44 + ", maxCycle=" + std::to_string(maxCycle);
45 ::TH1* resultHist = new ::TH1D( histName.c_str(), histTitle.c_str(),
46 nCBK, 0.0, nCBK );
47 // Set some properties of the histogram
48 resultHist->GetXaxis()->SetTitle("CutBookkeeper Name");
49 resultHist->GetYaxis()->SetTitle("nAcceptedEvents");
50
51 // Now, set the bin content for all bins
52 for (std::size_t i=0; i<nCBK; ++i){
53 const xAOD::CutBookkeeper* cbk = cbks[0];
54 const double nEvents = static_cast<double>(cbk->nAcceptedEvents());
55 const double error = std::sqrt(nEvents);
56 const std::string& name = cbk->name();
57 const int binIdx = static_cast<int>(i+1);
58 resultHist->SetBinContent(binIdx,nEvents);
59 resultHist->SetBinError(binIdx,error);
60 resultHist->GetXaxis()->SetBinLabel(binIdx,name.c_str());
61 }
62
63 // Done
64 return resultHist;
65}
66
67
69namespace
70{
71
72xAOD::CutBookkeeper *resolveLink( const xAOD::CutBookkeeper *old,
73 xAOD::CutBookkeeperContainer &contToUpdate,
74 const xAOD::CutBookkeeperContainer &otherCont,
75 const std::vector<size_t> &otherIndexMap )
76{
77 {
79 std::find(contToUpdate.begin(), contToUpdate.end(), old);
80 if (matchIter != contToUpdate.end()) {
81 return *matchIter;
82 }
83 }
84
85 {
87 std::find(otherCont.begin(), otherCont.end(), old);
88 if (matchIter != contToUpdate.end()) {
89 std::size_t pos = matchIter - otherCont.begin();
90 return contToUpdate[otherIndexMap[pos]];
91 }
92 }
93
94 // If we didn't find it, we need to add it
95 xAOD::CutBookkeeper *newEBK = new xAOD::CutBookkeeper(); // will be owned by the container
96 if (newEBK->usingPrivateStore()) { newEBK->releasePrivateStore(); }
97 newEBK->makePrivateStore(old);
98 contToUpdate.push_back(newEBK);
99 return newEBK;
100}
101
102} // unnamed namespace
103
104
107 const xAOD::CutBookkeeperContainer *otherCont )
108{
109 std::size_t origSize = contToUpdate->size();
110
111 // Vector of indices in contToUpdate of elements in otherCont.
112 std::vector<std::size_t> otherIndexMap(otherCont->size());
113 // Loop through otherCont.
114 // If element already in contToUpdate, update event counts, otherwise create new element
115 for (std::size_t i = 0; i < otherCont->size(); ++i) {
116 const xAOD::CutBookkeeper *otherEBK = otherCont->at(i);
117
118 // Loop through the container to be updated (contToUpdate) and see if we find a match
119 bool foundEBKToUpdate{false};
120 for (std::size_t j = 0; j < contToUpdate->size(); ++j) {
121 xAOD::CutBookkeeper *ebkToUpdate = contToUpdate->at(j);
122 // Check if they are identical, if so, update; else add otherEBK
123 if (otherEBK->isEqualTo(ebkToUpdate)) {
124 ebkToUpdate->setPayload(ebkToUpdate->payload() + otherEBK->payload());
125 otherIndexMap[i] = j;
126 foundEBKToUpdate = true;
127 break;
128 }
129 } // End: Inner loop over contToUpdate
130 if (!foundEBKToUpdate) {
131 xAOD::CutBookkeeper *newEBK = new xAOD::CutBookkeeper(); // will be owned by the container
132 if (newEBK->usingPrivateStore()) { newEBK->releasePrivateStore(); }
133 newEBK->makePrivateStore(otherEBK);
134 contToUpdate->push_back(newEBK);
135 std::size_t ebIdx = newEBK->index();
136 otherIndexMap[i] = ebIdx;
137 }
138 } // End: Outer loop over contToUpdate
139
140 // Now, we still need to fix the cross-referencing of the newly added CutBookkkeepers
141 for (std::size_t i = origSize; i < contToUpdate->size(); ++i) {
142 xAOD::CutBookkeeper *ebkToModify = contToUpdate->at(i);
143
144 // Parent check
145 if (ebkToModify->hasParent()) {
146 const xAOD::CutBookkeeper *oldParent = ebkToModify->parent();
147 const xAOD::CutBookkeeper *newParent = resolveLink (oldParent,
148 *contToUpdate,
149 *otherCont,
150 otherIndexMap);
151 ebkToModify->setParent (newParent);
152 } // Done fixing parent
153
154 // Children check
155 std::vector<xAOD::CutBookkeeper *> newChildren;
156 for ( std::size_t oldIdx = 0; oldIdx < ebkToModify->nChildren(); ++oldIdx) {
157 const xAOD::CutBookkeeper *oldEBK = ebkToModify->child(oldIdx);
158 newChildren.push_back(resolveLink(oldEBK,
159 *contToUpdate,
160 *otherCont,
161 otherIndexMap));
162 } // Done fixing children
163 ebkToModify->setChildren(newChildren);
164
165 // Used others check
166 std::vector<xAOD::CutBookkeeper *> newOthers;
167 for (std::size_t oldIdx = 0; oldIdx < ebkToModify->nUsedOthers(); ++oldIdx) {
168 const xAOD::CutBookkeeper *oldEBK = ebkToModify->usedOther(oldIdx);
169 newOthers.push_back(resolveLink(oldEBK,
170 *contToUpdate,
171 *otherCont,
172 otherIndexMap));
173 } // Done fixing used others
174 ebkToModify->setUsedOthers(newOthers);
175
176 // Siblings check
177 std::vector<xAOD::CutBookkeeper*> newSiblings;
178 for (std::size_t oldIdx = 0; oldIdx < ebkToModify->nSiblings(); ++oldIdx) {
179 const xAOD::CutBookkeeper *oldEBK = ebkToModify->sibling(oldIdx);
180 newSiblings.push_back(resolveLink(oldEBK,
181 *contToUpdate,
182 *otherCont,
183 otherIndexMap));
184 } // Done fixing siblings
185 ebkToModify->setSiblings(newSiblings);
186 } // Done fixing all cross references
187}
double cycle(double a, double b)
DataModel_detail::const_iterator< DataVector > const_iterator
Definition DataVector.h:838
const T * at(size_type n) const
Access an element, as an rvalue.
value_type push_back(value_type pElem)
Add an element to the end of the collection.
DataModel_detail::iterator< DataVector > iterator
Definition DataVector.h:842
const_iterator end() const noexcept
Return a const_iterator pointing past the end of the collection.
const_iterator begin() const noexcept
Return a const_iterator pointing at the beginning of the collection.
size_type size() const noexcept
Returns the number of elements in the collection.
void makePrivateStore()
Create a new (empty) private store for this object.
bool usingPrivateStore() const
Test to see if this object is currently using a private store.
void releasePrivateStore()
Release and free any private store associated with this object.
size_t index() const
Return the index of this element within its container.
int maxCycle() const
Get the maximum cycle number of any xAOD::CutBookkeepers in the container.
std::size_t nSiblings() const
Check if this CutBookkeeper has siblings.
void setPayload(const Payload &payload)
Set the whole payload object (which contains all counters) in one go.
const xAOD::CutBookkeeper_v1 * usedOther(std::size_t i) const
Get the usedOther at position i.
bool isEqualTo(const CutBookkeeper_v1 *eb) const
Test for the equality of this CutBookkeeper with another one.
std::size_t nChildren() const
Get the number of children CutBookkeepers of this CutBookkeeper.
const xAOD::CutBookkeeper_v1 * parent() const
Get the parent CutBookkeeper.
void setUsedOthers(const std::vector< CutBookkeeper_v1 * > &usedOthers)
Set all CutBookkeeper that are used by this one in one go.
const xAOD::CutBookkeeper_v1 * child(std::size_t i) const
Get the child at position i.
void setParent(const CutBookkeeper_v1 *parentEB)
Set the parent CutBookkeeper of this CutBookkeeper.
Payload payload() const
Get the whole payload object (which contains all counters) in one go.
const std::string & name() const
Get the name of this CutBookkeeper.
const xAOD::CutBookkeeper_v1 * sibling(std::size_t i) const
Get the sibling number i.
uint64_t nAcceptedEvents() const
Get the number of accepted events that this CutBookkeeper has seen.
void setChildren(const std::vector< CutBookkeeper_v1 * > &childrenEB)
Set all children of this CutBookkeeper in one go.
void setSiblings(const std::vector< CutBookkeeper_v1 * > &siblings)
Set all CutBookkeeper that are siblings to this one in one go.
std::size_t nUsedOthers() const
Check if this CutBookkeeper has used others.
bool hasParent() const
Check if there is a parent CutBookkeeper of this CutBookkeeper.
const int nEvents
::TH1 * nAcceptedEvents(const xAOD::CutBookkeeperContainer *cbkCont, const std::string &histName, int minCycle=0, int maxCycle=-1)
Make a histogram of the number of accepted events from a container.
void updateContainer(xAOD::CutBookkeeperContainer *contToUpdate, const xAOD::CutBookkeeperContainer *otherCont)
Helper function to update a container with information from another one.
CutBookkeeper_v1 CutBookkeeper
Define the latest version of the CutBookkeeper class.
CutBookkeeperContainer_v1 CutBookkeeperContainer
Define the latest version of the CutBookkeeperContainer class.