ATLAS Offline Software
eflowCellSubtractionFacilitator.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2023 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 // Athena Headers
7 //#include "eflowRec/eflowCellPosition.h"
8 
10 #include "CaloEvent/CaloCell.h"
11 #include "GaudiKernel/Bootstrap.h"
12 #include "GaudiKernel/IMessageSvc.h"
13 #include "GaudiKernel/ISvcLocator.h"
15 
16 // C++ Headers
17 #include <map>
18 
20  : AsgMessaging("eflowCellSubtractionFacilitator")
21 {}
22 
23 double
25  eflowRingSubtractionManager& cellSubtractionManager,
26  double trackEnergy,
27  xAOD::CaloCluster* tracksCluster,
28  eflowCellList& orderedCells,
29  bool& annFlag) const
30 {
31  std::vector<std::pair<xAOD::CaloCluster*, bool>> localClusterBoolPairVec(
32  1, std::pair(tracksCluster, false));
33  return subtractCells(
34  cellSubtractionManager, trackEnergy, localClusterBoolPairVec, orderedCells, annFlag);
35 }
36 
37 void
39  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters)
40 {
41  for (auto thisPair : tracksClusters)
42  updateClusterKinematics(thisPair.first);
43 }
44 
45 void
47  xAOD::CaloCluster* theCluster)
48 {
49  float oldEnergy = theCluster->e();
50  CaloClusterKineHelper::calculateKine(theCluster, true, true);
51  if (0.0 != oldEnergy) {
52  float energyAdjustment = theCluster->e() / oldEnergy;
53  theCluster->setRawE(theCluster->rawE() * energyAdjustment);
54  theCluster->setRawEta(theCluster->eta());
55  theCluster->setRawPhi(theCluster->phi());
56  }
57 }
58 
59 double
61  const std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters)
62 {
63  double eClustersOld = 0;
64  /* Summed energy of all clusters before subtraction */
65  for (auto thisPair : tracksClusters)
66  eClustersOld += (thisPair.first)->e();
67  return eClustersOld;
68 }
69 
70 double
72  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
73  CellIt beginRing,
74  CellIt endRing)
75 {
76  /* Get total energy of ringes from beginRing to endRing */
77 
78  double eRing(0.0);
79  for (CellIt it = beginRing; it != endRing; ++it) {
80  /* Loop over Rings */
81  for (auto thisCell : it->second) {
82  /* Loop over Cells */
83  std::pair<const CaloCell*, int> thisPair = thisCell;
84  xAOD::CaloCluster* clus = tracksClusters[thisPair.second].first;
85  CaloClusterCellLink::iterator theIterator =
87  double cellWeight = theIterator.weight();
88  eRing += thisPair.first->energy() * cellWeight;
89  }
90  }
91 
92  return eRing;
93 }
94 
95 void
97  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters, bool& annFlag)
98 {
99  for (auto& thisPair : tracksClusters) {
100  xAOD::CaloCluster* thisCluster = thisPair.first;
101  CaloClusterCellLink* theCellLink = thisCluster->getOwnCellLinks();
102  CaloClusterCellLink::iterator theFirstCell = theCellLink->begin();
103  CaloClusterCellLink::iterator theLastCell = theCellLink->end();
104  for (; theFirstCell != theLastCell; ++theFirstCell)
105  thisCluster->removeCell(*theFirstCell);
106  thisCluster->setCalE(0.0);
107  thisCluster->setRawE(0.0);
108  // set the subtracted status to true
109  thisPair.second = true;
110  }
111  annFlag = true;
112 }
113 
114 void
116  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
117  CellIt beginRing,
118  CellIt endRing,
119  double targetRingEnergy,
120  double eRings) const
121 {
122  for (CellIt itRing = beginRing; itRing != endRing; ++itRing) {
123  /* Loop over Rings */
124  for (auto thisCell : itRing->second) {
125  /* Loop over Cells */
126  std::pair<const CaloCell*, int> thisPair = thisCell;
127  xAOD::CaloCluster* cluster = tracksClusters[thisPair.second].first;
128  // flag this cluster as having had subtraction applied to it
129  tracksClusters[thisPair.second].second = true;
130  const CaloCell* cell = thisPair.first;
131  CaloClusterCellLink::iterator theIterator =
133  double oldCellWeight = theIterator.weight();
134  const double newCellWeight = oldCellWeight * targetRingEnergy / eRings;
135  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: Cluster with e "
136  << cluster->e()
137  << " is changing weight of cell with energy " << cell->e()
138  << " from " << oldCellWeight << " to " << newCellWeight);
139  theIterator.reweight(newCellWeight);
140  }
141  }
142 }
143 
144 void
146  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
147  CellIt beginRing,
148  CellIt endRing) const
149 {
150  /* Subtract full ring */
151 
152  for (CellIt itRing = beginRing; itRing != endRing; ++itRing) {
153  /* Loop over Rings */
154  for (auto thisCell : itRing->second) {
155  /* Loop over Cells */
156  std::pair<const CaloCell*, int> thisPair = thisCell;
157  xAOD::CaloCluster* cluster = tracksClusters[thisPair.second].first;
158  // flag this cluster as having had subtraction applied to it
159  tracksClusters[thisPair.second].second = true;
160  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: Cluster with e "
161  << cluster->e() << " is removing cell with e "
162  << thisPair.first->e());
163  cluster->removeCell(thisPair.first);
164  }
165  }
166 }
167 
168 bool
170  eflowRingSubtractionManager& cellSubtractionManager,
171  const std::pair<eflowCaloENUM, short>& ring,
172  double& eSubtracted,
173  const double eExpect,
174  eflowCellList& orderedCells,
175  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
176  bool& annFlag ) const
177 {
178  /* Subtract energy from ring, return TRUE if the whole expected energy is
179  * subtracted */
180 
181  const eflowCaloENUM subtLayer = ring.first;
182  const short ringNo = ring.second;
183 
184  const double r1 = ringNo * cellSubtractionManager.ringThickness(subtLayer);
185  const double r2 =
186  (ringNo + 1) * cellSubtractionManager.ringThickness(subtLayer);
187 
188  CellIt beginRing = orderedCells.getLowerBound(subtLayer, r1);
189  CellIt endRing = orderedCells.getLowerBound(subtLayer, r2);
190 
191  /* Get total energy of Rings from beginRing to endRing */
192  double eRings = getRingsEnergy(tracksClusters, beginRing, endRing);
193 
194  if (eSubtracted + eRings > eExpect) {
195  /* Subtract partial ring */
196 
197  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: Subtracting partial ring, "
198  "eSubtracted, eRings and eExpect are "
199  << eSubtracted << ", " << eRings << ", " << eExpect);
200 
201  /* Target ring energy is ring energy minus the energy that still needs to be
202  * subtracted */
203  double targetRingEnergy = eRings - (eExpect - eSubtracted);
204  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: targetRingEnergy is "
205  << targetRingEnergy);
207  tracksClusters, beginRing, endRing, targetRingEnergy, eRings);
208  eSubtracted = eExpect;
209 
210  /* Update the cluster four-momenta having done the subtraction */
211  updateClusterKinematics(tracksClusters);
212 
213  return true;
214 
215  } else {
216  /* Subtract full ring */
217 
218  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: Subtracting full ring ");
219 
220  subtractFullRings(tracksClusters, beginRing, endRing);
221  orderedCells.deleteFromList(beginRing, endRing);
222  eSubtracted += eRings;
223 
224  /* If no energy left */
225  double eClustersOld = getTotalEnergy(tracksClusters);
226  if (fabs(eClustersOld - eSubtracted) < 1.0e-6 * eClustersOld) {
227  /* Annihilate clusters, clear orderedCells, and update subtracted cluster
228  * kinematics */
229  annihilateClusters(tracksClusters,annFlag);
230  orderedCells.eraseList();
231  updateClusterKinematics(tracksClusters);
232 
233  return true;
234  }
235 
236  return false;
237  }
238 }
239 
240 bool
242  const double eExpect,
243  xAOD::CaloCluster* cluster,
244  const CaloCell* cell)
245 {
246 
247  CaloClusterCellLink::iterator theIterator =
249  double oldCellWeight = theIterator.weight();
250  double oldCellEnergy = cell->energy() * oldCellWeight;
251 
252  if (oldCellEnergy != 0. && eSubtracted + oldCellEnergy > eExpect) {
253  /* Target cell energy is cell energy minus the energy that still needs to be
254  * subtracted */
255  double targetCellEnergy = oldCellEnergy - (eExpect - eSubtracted);
256 
257  double newCellWeight = oldCellWeight * targetCellEnergy / oldCellEnergy;
258  theIterator.reweight(newCellWeight);
259 
260  eSubtracted = eExpect;
261 
262  /* Update the cluster four-momenta having done the subtraction */
263  updateClusterKinematics(cluster);
264 
265  return true;
266 
267  } else {
268  cluster->removeCell(cell);
269  eSubtracted += oldCellEnergy;
270 
271  /* Update the clusters having done the subtraction */
272  updateClusterKinematics(cluster);
273  return false;
274  }
275 }
276 
277 bool
279  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
280  double eSubtracted,
281  const double eExpect,
282  eflowCellList& reorderedCells)
283 {
284  CellIt itCellPosition = reorderedCells.begin();
285  CellIt endCellPosition = reorderedCells.end();
286  while (itCellPosition != endCellPosition) {
287  /* Loop cells */
288  std::vector<std::pair<const CaloCell*, int>>::iterator itEntry =
289  itCellPosition->second.begin();
290  std::vector<std::pair<const CaloCell*, int>>::iterator endEntry =
291  itCellPosition->second.end();
292  for (; itEntry != endEntry; ++itEntry) {
293  const std::pair<const CaloCell*, int> thisPair = *itEntry;
294  xAOD::CaloCluster* cluster = tracksClusters[thisPair.second].first;
295  // flag this cluster as having had subtraction applied to it
296  tracksClusters[thisPair.second].second = true;
297  const CaloCell* cell = thisPair.first;
298  bool isFinished = subtractCaloCell(eSubtracted, eExpect, cluster, cell);
299  if (isFinished)
300  return true;
301  }
302  /* Erase the CellPosition from the cell list */
303  CellIt tmp = itCellPosition;
304  ++itCellPosition;
305  reorderedCells.deleteFromList(tmp);
306  }
307  return false;
308 }
309 
310 double
312  eflowRingSubtractionManager& cellSubtractionManager,
313  double trackEnergy,
314  std::vector<std::pair<xAOD::CaloCluster*, bool>>& tracksClusters,
315  eflowCellList& orderedCells,
316  bool& annFlag) const
317 {
318 
319  const double eExpect = cellSubtractionManager.fudgeMean() * trackEnergy;
320  const double sigmaEExpect =
321  cellSubtractionManager.fudgeStdDev() * trackEnergy;
322  ATH_MSG_DEBUG("eflowCellSubtractionFacilitator: For track with trackEnergy "
323  << trackEnergy << " expect to subtract " << eExpect
324  << " with width of " << sigmaEExpect);
325 
326  double eSubtracted = 0.0;
327 
328  /*
329  * Ring subtraction
330  */
331  std::map<double, RingId>::const_iterator ringIt =
332  cellSubtractionManager.rankBegin();
333  std::map<double, RingId>::const_iterator ringEnd =
334  cellSubtractionManager.rankEnd();
335  for (; ringIt != ringEnd; ++ringIt) {
336  bool isFinished = subtractRings(cellSubtractionManager,
337  ringIt->second,
338  eSubtracted,
339  eExpect,
340  orderedCells,
341  tracksClusters,
342  annFlag);
343  if (isFinished) {
344  return sigmaEExpect;
345  }
346  }
347 
348  /* Update the cluster four-momenta */
349  updateClusterKinematics(tracksClusters);
350 
351  if (orderedCells.mapSize() <= 0 || eSubtracted >= eExpect) {
352  return sigmaEExpect;
353  }
354 
355  /*
356  * Cell subtraction
357  */
358  /* Increasing dR (not by layer) for cell subtraction */
359  orderedCells.reorderWithoutLayers();
360 
361  bool isFinished =
362  subtractReorderedCells(tracksClusters, eSubtracted, eExpect, orderedCells);
363  if (isFinished) {
364  return sigmaEExpect;
365  }
366 
367  /* Update the cluster four-momenta */
368  updateClusterKinematics(tracksClusters);
369 
370  return sigmaEExpect;
371 }
372 
375  xAOD::CaloCluster* thisCluster,
376  const CaloCell* thisCell)
377 {
378 
379  // SLOW! Can we move to directly work with iterators in future?
380 
381  // We have to use non-const iterators so that we are allowed to modify the
382  // cell weights
383  CaloClusterCellLink* theCells = thisCluster->getOwnCellLinks();
384 
385  CaloClusterCellLink::iterator itCell = theCells->begin();
386  CaloClusterCellLink::iterator endCell = theCells->end();
387  for (; itCell != endCell; ++itCell) {
388  const CaloCell* pCell = (*itCell);
389  if (pCell == thisCell) { // Pointer comparison!
390  return itCell;
391  }
392  }
393 
394  // if no match is found then return end of container
395  return endCell;
396 }
xAOD::iterator
JetConstituentVector::iterator iterator
Definition: JetConstituentVector.cxx:68
xAOD::CaloCluster_v1::phi
virtual double phi() const
The azimuthal angle ( ) of the particle.
Definition: CaloCluster_v1.cxx:256
eflowCellSubtractionFacilitator::getTotalEnergy
static double getTotalEnergy(const std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters)
Definition: eflowCellSubtractionFacilitator.cxx:60
CaloClusterKineHelper.h
xAOD::CaloCluster_v1::rawE
flt_t rawE() const
eflowCellList::reorderWithoutLayers
void reorderWithoutLayers()
Definition: eflowCellList.cxx:72
eflowCellList::deleteFromList
void deleteFromList(CellIt &start, CellIt &end)
Definition: eflowCellList.h:71
ReadCellNoiseFromCool.cell
cell
Definition: ReadCellNoiseFromCool.py:53
getMessageSvc.h
singleton-like access to IMessageSvc via open function and helper
eflowRingSubtractionManager::rankBegin
std::map< double, RingId >::const_iterator rankBegin() const
Definition: eflowRingSubtractionManager.h:44
skel.it
it
Definition: skel.GENtoEVGEN.py:423
CaloCell.h
eflowCellSubtractionFacilitator::subtractPartialRings
void subtractPartialRings(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, CellIt beginRing, CellIt endRing, double targetRingEnergy, double eRing) const
Definition: eflowCellSubtractionFacilitator.cxx:115
eflowCellList::end
CellIt end()
Definition: eflowCellList.h:57
eflowRingSubtractionManager::fudgeStdDev
double fudgeStdDev() const
Definition: eflowRingSubtractionManager.h:38
eflowCellList::begin
CellIt begin()
Definition: eflowCellList.h:56
eflowCellList
Concrete class derived class from pure virtual eflowAbstractCellList.
Definition: eflowCellList.h:42
eflowCellSubtractionFacilitator::subtractCells
double subtractCells(eflowRingSubtractionManager &ringSubtractionManager, double trackEnergy, xAOD::CaloCluster *tracksClus, eflowCellList &orderedCells, bool &annFlag) const
Definition: eflowCellSubtractionFacilitator.cxx:24
eflowCellSubtractionFacilitator::eflowCellSubtractionFacilitator
eflowCellSubtractionFacilitator()
Definition: eflowCellSubtractionFacilitator.cxx:19
eflowCellSubtractionFacilitator::subtractRings
bool subtractRings(eflowRingSubtractionManager &ringSubtractionManager, const std::pair< eflowCaloENUM, short > &ring, double &eSubtracted, const double eExpect, eflowCellList &orderedCells, std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, bool &annFlag) const
Definition: eflowCellSubtractionFacilitator.cxx:169
xAOD::CaloCluster_v1
Description of a calorimeter cluster.
Definition: CaloCluster_v1.h:59
eflowCellSubtractionFacilitator::subtractReorderedCells
static bool subtractReorderedCells(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, double eSubtracted, const double eExpect, eflowCellList &orderedCells)
Definition: eflowCellSubtractionFacilitator.cxx:278
xAOD::CaloCluster_v1::setRawE
void setRawE(flt_t)
Set Energy for signal state UNCALIBRATED.
Definition: CaloCluster_v1.cxx:284
xAOD::CaloCluster_v1::removeCell
bool removeCell(const CaloCell *ptr)
Method to remove a cell to the cluster (slow!) (Beware: Kinematics not updated!)
Definition: CaloCluster_v1.cxx:923
xAOD::CaloCluster_v1::eta
virtual double eta() const
The pseudorapidity ( ) of the particle.
Definition: CaloCluster_v1.cxx:251
ATH_MSG_DEBUG
#define ATH_MSG_DEBUG(x)
Definition: AthMsgStreamMacros.h:29
eflowCellSubtractionFacilitator::getRingsEnergy
static double getRingsEnergy(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, CellIt beginRing, CellIt endRing)
Definition: eflowCellSubtractionFacilitator.cxx:71
eflowCellSubtractionFacilitator::annihilateClusters
static void annihilateClusters(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, bool &annFlag)
Definition: eflowCellSubtractionFacilitator.cxx:96
eflowRingSubtractionManager::fudgeMean
double fudgeMean() const
Definition: eflowRingSubtractionManager.h:37
xAOD::CaloCluster_v1::setRawEta
void setRawEta(flt_t)
Set for signal state UNCALIBRATED.
Definition: CaloCluster_v1.cxx:289
eflowCellList::eraseList
void eraseList()
Definition: eflowCellList.h:76
eflowCellSubtractionFacilitator::subtractFullRings
void subtractFullRings(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters, CellIt beginRing, CellIt endRing) const
Definition: eflowCellSubtractionFacilitator.cxx:145
DeMoUpdate.tmp
string tmp
Definition: DeMoUpdate.py:1167
eflowRingSubtractionManager
This stores information, a rank and ring thickness, about cell rings in an ordered way.
Definition: eflowRingSubtractionManager.h:31
eflowCellSubtractionFacilitator.h
eflowCellSubtractionFacilitator::updateClusterKinematics
static void updateClusterKinematics(std::vector< std::pair< xAOD::CaloCluster *, bool >> &tracksClusters)
Definition: eflowCellSubtractionFacilitator.cxx:38
xAOD::CaloCluster_v1::setCalE
void setCalE(flt_t)
Set Energy for signal state CALIBRATED.
Definition: CaloCluster_v1.cxx:306
CellIt
std::map< eflowCellPosition, std::vector< std::pair< const CaloCell *, int > > >::iterator CellIt
Definition: eflowAbstractCellList.h:25
eflowCellList::mapSize
int mapSize()
Definition: eflowCellList.h:70
DiTauMassTools::MaxHistStrategyV2::e
e
Definition: PhysicsAnalysis/TauID/DiTauMassTools/DiTauMassTools/HelperFunctions.h:26
eflowCalo::LAYER
LAYER
Definition: eflowCaloRegions.h:36
CaloCell
Data object for each calorimeter readout cell.
Definition: CaloCell.h:57
xAOD::CaloCluster_v1::getOwnCellLinks
CaloClusterCellLink * getOwnCellLinks()
Get a pointer to the owned CaloClusterCellLink object (non-const version)
Definition: CaloCluster_v1.h:762
CaloClusterKineHelper::calculateKine
static void calculateKine(xAOD::CaloCluster *clu, const bool useweight=true, const bool updateLayers=true, const bool useGPUCriteria=false)
Helper class to calculate cluster kinematics based on cells.
Definition: CaloClusterKineHelper.cxx:223
eflowCellList::getLowerBound
CellIt getLowerBound(eflowCaloENUM layer, double r)
Definition: eflowCellList.h:59
eflowCellSubtractionFacilitator::subtractCaloCell
static bool subtractCaloCell(double &eSubtracted, const double eExpect, xAOD::CaloCluster *cluster, const CaloCell *cell)
Definition: eflowCellSubtractionFacilitator.cxx:241
xAOD::CaloCluster_v1::e
virtual double e() const
The total energy of the particle.
Definition: CaloCluster_v1.cxx:265
eflowRingSubtractionManager::rankEnd
std::map< double, RingId >::const_iterator rankEnd() const
Definition: eflowRingSubtractionManager.h:45
xAOD::CaloCluster_v1::setRawPhi
void setRawPhi(flt_t)
Set for signal state UNCALIBRATED.
Definition: CaloCluster_v1.cxx:294
eflowCellSubtractionFacilitator::getCellIterator
static CaloClusterCellLink::iterator getCellIterator(xAOD::CaloCluster *thisCluster, const CaloCell *thisCell)
Definition: eflowCellSubtractionFacilitator.cxx:374
eflowRingSubtractionManager::ringThickness
double ringThickness(eflowCaloENUM layer) const
Definition: eflowRingSubtractionManager.h:47