ATLAS Offline Software
Loading...
Searching...
No Matches
eflowCaloObject.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2026 CERN for the benefit of the ATLAS collaboration
3*/
4
5/********************************************************************
6
7NAME: eflowCaloObject.cxx
8PACKAGE: offline/Reconstruction/eflowRec
9
10AUTHORS: D.R.Tovey, M.Hodgkinson and T.Velz
11CREATED: 22nd November, 2004
12
13********************************************************************/
14
15#include "eflowCaloObject.h"
16#include "eflowRecTrack.h"
17#include "eflowRecCluster.h"
23
25
26void eflowCaloObject::addTrackClusterLinks(const std::vector<eflowTrackClusterLink*> &trackClusterLink) {
27 for (auto *ptr : trackClusterLink) {
29 }
30}
31
32 void eflowCaloObject::addTracks(const std::vector<eflowRecTrack*> &tracks) {
33 m_eflowRecTracks.insert(m_eflowRecTracks.end(), tracks.begin(), tracks.end());
34 }
35
36 void eflowCaloObject::addClusters(const std::vector<eflowRecCluster*> &clusters) {
37 m_eflowRecClusters.insert(m_eflowRecClusters.end(), clusters.begin(), clusters.end());
38 }
39
41 double expectedEnergy(0.0);
42 for(unsigned iTrack=0; iTrack < nTracks(); ++iTrack) {
43 if (!efRecTrack(iTrack)->isInDenseEnvironment()) expectedEnergy += efRecTrack(iTrack)->getEExpect();
44 }
45 return expectedEnergy;
46}
47
49 double expectedVariance(0.0);
50 for(unsigned iTrack=0; iTrack < nTracks(); ++iTrack) {
51 if (!efRecTrack(iTrack)->isInDenseEnvironment()) expectedVariance += efRecTrack(iTrack)->getVarEExpect();
52 }
53 return expectedVariance;
54}
55
57 double clusterEnergy(0.0);
58 for(unsigned iCluster=0; iCluster < nClusters(); ++iCluster) {
59 clusterEnergy += efRecCluster(iCluster)->getCluster()->e();
60 }
61 return clusterEnergy;
62}
63
65const PFEnergyPredictorTool* energyP, bool useLegacyEnergyBinIndexing){
66
67 for (auto *thisEfRecTrack : m_eflowRecTracks) {
68
69 std::vector<eflowRecCluster*> matchedClusters;
70 const std::vector<eflowTrackClusterLink*>& links = thisEfRecTrack->getClusterMatches();
71 for (auto* itLink : links) {
72 matchedClusters.push_back(itLink->getCluster());
73 }
74
75 double trackEM1eta = thisEfRecTrack->getTrackCaloPoints().getEM1eta();
76 /* if a track is in the forward EM (2.5 < eta < 3.2) then there is no EM1 -> need to use EM2 */
77 if(trackEM1eta<-998.) trackEM1eta = thisEfRecTrack->getTrackCaloPoints().getEM2eta();
78 /* if a track is not in the EM region (3.2 < eta < 4.0) then should use FCAL0 */
79 if(trackEM1eta<-998.) trackEM1eta = thisEfRecTrack->getTrackCaloPoints().getFCAL0eta();
80
81 double trackE = thisEfRecTrack->getTrack()->e();
82
83 if (!binnedParameters->binExists(trackE, trackEM1eta)) {
84 thisEfRecTrack->setHasBin(false);
85 return;
86 }
87
88 /* Determine the LFI */
89 integrator->measureNewClus(matchedClusters, thisEfRecTrack);
90 eflowFirstIntENUM j1st = integrator->getFirstIntLayer();
91
92 /*Save j1st info */
93 thisEfRecTrack->setLayerHED(j1st);
94
95 /* Get parameters for j1st */
96 eflowRingSubtractionManager& cellSubtractionManager = thisEfRecTrack->getCellSubtractionManager();
97 cellSubtractionManager.getOrdering(binnedParameters, trackE, trackEM1eta, j1st,useLegacyEnergyBinIndexing);
98
99 /* Set expected energy in the eflowRecTrack object */
100 const double expectedEnergy = energyP ? energyP->nnEnergyPrediction(thisEfRecTrack) : cellSubtractionManager.fudgeMean() * thisEfRecTrack->getTrack()->e();
101 const double expectedEnergySigma = std::fabs(cellSubtractionManager.fudgeStdDev() * thisEfRecTrack->getTrack()->e());
102
103 const std::vector<eflowTrackClusterLink*>* bestClusters_015 = thisEfRecTrack->getAlternativeClusterMatches("cone_015");
104 const std::vector<eflowTrackClusterLink*>* bestClusters_02 = thisEfRecTrack->getAlternativeClusterMatches("cone_02");
105
106 //First we calculate how much energy is found in a cone of 0.15
107 float totalE_015 = 0.0;
108
109 //This pointer can be a nullptr if no clusters were matched to a track in dR < 0.15
110 if (bestClusters_015){
111 for (eflowTrackClusterLink* thisLink : *bestClusters_015){
112 eflowRecCluster* thisBestCluster = thisLink->getCluster();
113 if (thisBestCluster){
114 const xAOD::CaloCluster* theCluster = thisBestCluster->getCluster();
115 if (theCluster) {
116 if (theCluster->e()>0.0){
117 totalE_015 += theCluster->e();
118 }
119 }
120 }
121 }
122 }//if vector of 0.15 clusters exists
123
124 double pull_015 = NAN;
125 if (expectedEnergySigma > 1e-6 ) pull_015 = (totalE_015-expectedEnergy)/expectedEnergySigma;
126 thisEfRecTrack->setpull15(pull_015);
127
128 double trackPt = thisEfRecTrack->getTrack()->pt();
129 //If the looked up expected energy deposit was 0.0, then pull_015 is NAN. In that case we should not try to apply the 2D cut described below.
130 if (!std::isnan(pull_015)){
131 //We use a 2D cut in the pull_015 and log10 of track pt plane to define a dense environment - if too dense then we disable the charged shower subtraction
132 //The cut values are such that above a track pt of 40 GeV we are very agrressive about disabling the cell by cell charged shower subtraction.
133 //The specific cut values were found by optimising the jet resolutions in the run 2 data taking environment.
134 //Further details can be found in these slides from C. Young:
135 //https://indico.cern.ch/event/396923/contributions/949333/attachments/795878/1090871/Presentation.pdf
136 if (pull_015 > 0.0 + (log10(40000)-log10(trackPt))*33.2 && 0.0 != expectedEnergySigma && bestClusters_015 && bestClusters_02){
137 thisEfRecTrack->setSubtracted(); //this tricks eflowRec into thinking this track was subtracted, and hence no further subtraction will be done
138 thisEfRecTrack->setIsInDenseEnvironment();
139 //recalculate the LHED and the ordering and find the new expected E + sigma of expected E (the new LHED can change the latter two values we find in the look up tables)
140 //we use a larger cone of 0.2 for this
141 std::vector<eflowRecCluster*> theBestEfRecClusters_02;
142 for (eflowTrackClusterLink* thisLink : *bestClusters_02) if (thisLink->getCluster()->getCluster()->e() > 0.0) theBestEfRecClusters_02.push_back(thisLink->getCluster());
143 integrator->measureNewClus(theBestEfRecClusters_02, thisEfRecTrack);
144 j1st = integrator->getFirstIntLayer();
145 cellSubtractionManager.getOrdering(binnedParameters, trackE, trackEM1eta, j1st,useLegacyEnergyBinIndexing);
146 thisEfRecTrack->setEExpect(cellSubtractionManager.fudgeMean() * trackE, std::fabs(cellSubtractionManager.fudgeStdDev()*trackE)*std::fabs(cellSubtractionManager.fudgeStdDev()*trackE));
147 }
148 else {
149 thisEfRecTrack->setEExpect(expectedEnergy, expectedEnergySigma*expectedEnergySigma);
150 }//ok to do subtraction, and so we just set the usual expected E + sigma of expected E needed for subtraction
151 }
152 }
153}
float nnEnergyPrediction(const eflowRecTrack *ptr) const
void addTracks(const std::vector< eflowRecTrack * > &tracks)
double getExpectedVariance() const
std::vector< eflowRecTrack * > m_eflowRecTracks
double getClusterEnergy() const
void addTrackClusterLinks(const std::vector< eflowTrackClusterLink * > &trackClusterLink)
void addClusters(const std::vector< eflowRecCluster * > &clusters)
void addTrackClusterLink(eflowTrackClusterLink *trackClusterLink)
unsigned nClusters() const
const eflowRecTrack * efRecTrack(int i) const
std::vector< eflowRecCluster * > m_eflowRecClusters
unsigned nTracks() const
double getExpectedEnergy() const
void simulateShower(eflowLayerIntegrator *integrator, const eflowEEtaBinnedParameters *binnedParameters, const PFEnergyPredictorTool *energyP, bool useLegacyEnergyBinIndexing)
const eflowRecCluster * efRecCluster(int i) const
bool binExists(double e, double eta) const
Inherits from eflowEEtaBinBase.
This class calculates the LHED (Layer of Highest Energy Density) in a cluster or group of clusters.
void measureNewClus(const xAOD::CaloCluster *clus, const eflowTrackCaloPoints &trackCalo)
eflowFirstIntENUM getFirstIntLayer() const
This class extends the information about a xAOD::CaloCluster.
xAOD::CaloCluster * getCluster()
double getEExpect() const
double getVarEExpect() const
This stores information, a rank and ring thickness, about cell rings in an ordered way.
bool getOrdering(const eflowEEtaBinnedParameters *binnedParameters, double e, double eta, eflowFirstIntENUM j1st, bool useLegacyEnergyBinIndexing)
virtual double e() const
The total energy of the particle.
eflowFirstIntRegions::J1STLAYER eflowFirstIntENUM
CaloCluster_v1 CaloCluster
Define the latest version of the calorimeter cluster class.