ATLAS Offline Software
TrigHitDVHypoTool.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2021 CERN for the benefit of the ATLAS collaboration
3 
4  * Trigger Hypo Tool, that is aimed at triggering displaced vertex
5  * author Kunihiro Nagano <kunihiro.nagano@cern.ch> - KEK
6 */
7 
11 #include "GaudiKernel/PhysicalConstants.h"
12 #include "TrigHitDVHypoTool.h"
13 
14 using namespace TrigCompositeUtils;
15 
16 // ------------------------------------------------------------------------------------------------
17 // ------------------------------------------------------------------------------------------------
18 
20  const std::string& name,
21  const IInterface* parent )
22  : AthAlgTool( type, name, parent ),
23  m_decisionId( HLT::Identifier::fromToolName( name ) ) {}
24 
26 
27 // ------------------------------------------------------------------------------------------------
28 // ------------------------------------------------------------------------------------------------
29 
31 {
32  ATH_MSG_DEBUG( "Initialization completed successfully:" );
33  ATH_MSG_DEBUG( " cutJetPtGeV = " << m_cutJetPtGeV );
34  ATH_MSG_DEBUG( " cutJetEta = " << m_cutJetEta );
35  ATH_MSG_DEBUG( " effBDT = " << m_effBDT );
36  ATH_MSG_DEBUG( " doSPseed = " << m_doSPseed );
37 
38  ATH_MSG_DEBUG( "Tool configured for chain/id: " << m_decisionId );
39 
40  return StatusCode::SUCCESS;
41 }
42 
43 // ------------------------------------------------------------------------------------------------
44 // ------------------------------------------------------------------------------------------------
45 
47 {
48  const float defaultBDTthreshold = 0.33482806; // 70% effi at mu=60
49 
50  if( mu<10 || 80<mu ) return defaultBDTthreshold;
51  if( eff<0.5 || 1.<eff ) return defaultBDTthreshold;
52 
53  // pol4*4 fitting
54  const std::vector<std::vector<float>> par = {
55  { 2.9044277, -6.3516751, -4.0085606, 25.456841, -18.208683 },
56  { 0.066196623, -0.098157640, 0.027455008, -0.19900459, 0.16721183 },
57  { -0.00091570959, 1.4831281e-05, 0.0028768317, -0.00053051617, 0.00040427140 },
58  { 2.5249073e-06, 1.7882097e-06, -7.1741129e-06, -9.7309257e-07, -3.2151707e-05 },
59  { -8.2905419e-08, 3.9337893e-07, -5.8968642e-07, 2.6341441e-07, 2.4551736e-07 }
60  };
61 
62  float thres = defaultBDTthreshold;
63  for (size_t i = 0; i < 5; i++) {
64  for (size_t j = 0; j < 5; j++) {
65  float tmp = par[i][j];
66  for (size_t imu = 0; imu < i; imu++) tmp *= mu;
67  for (size_t jeff = 0; jeff < j; jeff++) tmp *= eff;
68  thres += tmp;
69  }
70  }
71 
72  return thres;
73 }
74 
75 // ------------------------------------------------------------------------------------------------
76 // ------------------------------------------------------------------------------------------------
77 
79 {
80  const float defaultBDTthreshold = 0.27072057; // 70% effi at mu=60
81 
82  if( mu<10 || 80<mu ) return defaultBDTthreshold;
83  if( eff<0.5 || 1.<eff ) return defaultBDTthreshold;
84 
85  // pol4*4 fitting
86  const std::vector<std::vector<float>> par = {
87  { 1.8938782, -1.7096217, -8.7938548, 19.779355, -10.656187 },
88  { 0.048863505, -0.18192399, 0.30932576, -0.11527519, -0.13591443 },
89  { -0.00060239060, 0.00096109052, -0.0015378287, -0.0030951666, 0.0063958596 },
90  { 2.5855329e-06, 7.3128949e-06, -6.9676558e-06, 4.2141737e-05, -7.1813827e-05 },
91  { -4.8077006e-08, 1.0646790e-07, -8.0539473e-08, -1.9821312e-07, 3.4713098e-07 }
92  };
93 
94  float thres = defaultBDTthreshold;
95  for (size_t i = 0; i < 5; i++) {
96  for (size_t j = 0; j < 5; j++) {
97  float tmp = par[i][j];
98  for (size_t imu = 0; imu < i; imu++) tmp *= mu;
99  for (size_t jeff = 0; jeff < j; jeff++) tmp *= eff;
100  thres += tmp;
101  }
102  }
103 
104  return thres;
105 }
106 
107 // ------------------------------------------------------------------------------------------------
108 // ------------------------------------------------------------------------------------------------
109 
111 {
112  const float defaultBDTthreshold = 0.03773; // 70% effi at mu=60
113 
114  if( mu<10 || 60<mu ) return defaultBDTthreshold;
115 
116  // pol4 fitting
117  const float par0 = 0.404727;
118  const float par1 = -0.00344154;
119  const float par2 = -6.54218e-05;
120  const float par3 = -3.39841e-07;
121  const float par4 = 9.93062e-09;
122 
123  float thres = par0 + par1*mu + par2*mu*mu + par3*mu*mu*mu + par4*mu*mu*mu*mu;
124  return thres;
125 }
126 
127 // ------------------------------------------------------------------------------------------------
128 // ------------------------------------------------------------------------------------------------
129 
130 StatusCode TrigHitDVHypoTool::decide( std::vector<HitDVHypoInfo>& toolInputs ) const
131 {
132  size_t numTrigger = m_cutJetPtGeV.size();
133  size_t numHitDVs = toolInputs.size();
134 
135  ATH_MSG_DEBUG( " Number of HitDVs = " << numHitDVs );
136 
137  if ( numTrigger == 1 ) {
138  ATH_MSG_DEBUG( " Applying selection of single for " << m_decisionId );
139  return inclusiveSelection(toolInputs);
140  }
141  else {
142  ATH_MSG_DEBUG( " Applying selection of multiplicity for " << m_decisionId );
143  return multiplicitySelection(toolInputs);
144  }
145 
146  return StatusCode::SUCCESS;
147 }
148 
149 // ------------------------------------------------------------------------------------------------
150 // ------------------------------------------------------------------------------------------------
151 
152 StatusCode TrigHitDVHypoTool::inclusiveSelection(std::vector<HitDVHypoInfo>& toolInputs) const
153 {
154  bool isJetCutPassed = false;
155  for ( auto& input: toolInputs ) {
156  if ( TrigCompositeUtils::passed( m_decisionId.numeric(), input.previousDecisionsIDs ) ) {
157  if ( decideOnSingleObject( input, 0, true )==true ) {
158  isJetCutPassed = true;
159  break;
160  }
161  }
162  }
163 
164  if( ! isJetCutPassed ) return StatusCode::SUCCESS;
165 
166  bool isPassed = false;
167  unsigned int idv=0;
168  for ( auto& input: toolInputs ) {
169  ATH_MSG_DEBUG( " --- idv=" << idv << " ---");
170  if ( TrigCompositeUtils::passed( m_decisionId.numeric(), input.previousDecisionsIDs ) ) {
171  if ( decideOnSingleObject( input, 0, false )==true ) {
172  ATH_MSG_DEBUG( " Passed selection --> adding DecisionID");
173  isPassed = true;
175  }
176  } else {
177  ATH_MSG_DEBUG( " Not match DecisionID: " << m_decisionId );
178  }
179  ++idv;
180  }
181 
182  ATH_MSG_DEBUG( "Inclusive selection isPassed = " << isPassed);
183  return StatusCode::SUCCESS;
184 }
185 
186 // ------------------------------------------------------------------------------------------------
187 // ------------------------------------------------------------------------------------------------
188 
189 StatusCode TrigHitDVHypoTool::multiplicitySelection(std::vector<HitDVHypoInfo>& toolInputs) const
190 {
191  unsigned int n_jetpassed = 0;
192  for ( size_t cutIndex=0; cutIndex < m_cutJetPtGeV.size(); ++cutIndex ) {
193  bool isJetCutPassed = false;
194  for ( auto& input: toolInputs ) {
195  if ( TrigCompositeUtils::passed( m_decisionId.numeric(), input.previousDecisionsIDs ) ) {
196  if ( decideOnSingleObject( input, cutIndex, true )==true ) {
197  isJetCutPassed = true;
198  break;
199  }
200  }
201  }
202  if( isJetCutPassed ) ++n_jetpassed;
203  }
204  if( n_jetpassed < m_cutJetPtGeV.size() ) return StatusCode::SUCCESS;
205 
206  //
207  HLT::Index2DVec passingSelection( m_cutJetPtGeV.size() );
208 
209  for ( size_t cutIndex=0; cutIndex < m_cutJetPtGeV.size(); ++cutIndex ) {
210  size_t elementIndex{ 0 };
211  for ( auto& input: toolInputs ) {
212  if ( TrigCompositeUtils::passed( m_decisionId.numeric(), input.previousDecisionsIDs ) ) {
213  if ( decideOnSingleObject( input, cutIndex, false ) == true ) {
214  ATH_MSG_DEBUG( "Pass through selection " << m_decisionId << " : Event[" << elementIndex << "]" );
215  passingSelection[cutIndex].push_back( elementIndex );
216  }
217  }
218  else {
219  ATH_MSG_DEBUG( "Not match DecisionID " << m_decisionId );
220  }
221  elementIndex++;
222  }
223  // If no object passes the selection, multipul selection should stop.
224  if ( passingSelection[cutIndex].empty() ) {
225  ATH_MSG_DEBUG( "No object passed selection " << cutIndex << " rejecting" );
226  return StatusCode::SUCCESS;
227  }
228  }
229 
230  std::set<size_t> passingIndices;
231  HLT::elementsInUniqueCombinations( passingSelection, passingIndices );
232 
233  if ( passingIndices.empty() ) {
234  ATH_MSG_DEBUG( "No track passed through selection " << m_decisionId );
235  return StatusCode::SUCCESS;
236  }
237 
238  for ( auto idx: passingIndices ) {
239  ATH_MSG_DEBUG( "track[" << idx << "] passes through Chain/ID " << m_decisionId << " with pT" );
240  TrigCompositeUtils::addDecisionID( m_decisionId.numeric(), toolInputs[idx].decision );
241  }
242 
243  return StatusCode::SUCCESS;
244 }
245 
246 // ------------------------------------------------------------------------------------------------
247 // ------------------------------------------------------------------------------------------------
248 
249 bool TrigHitDVHypoTool::decideOnSingleObject( HitDVHypoInfo& input, size_t cutIndex, bool isOnlyJetCut ) const
250 {
251  float ptThreshold = m_cutJetPtGeV[cutIndex];
252  float etaThreshold = m_cutJetEta[cutIndex];
253  float eff = m_effBDT[cutIndex];
254 
255  const xAOD::TrigComposite* dv = input.hitDV;
256  int seed_type = dv->getDetail<int> ("hitDV_seed_type");
257  float seed_eta = dv->getDetail<float>("hitDV_seed_eta");
258  float seed_pt = dv->getDetail<float>("hitDV_seed_pt");
259 
260  // if only jet pt/eta cut
261  if( isOnlyJetCut ) {
262  if( seed_type != SeedType::HLTJet ) return false;
263  if( std::abs(seed_eta) > etaThreshold ) return false;
264  if( seed_pt < ptThreshold ) return false;
265  // passed
266  return true;
267  }
268 
269  if( input.isSPOverflow ) return true;
270 
271  // normal cut
272  bool doSPseed = m_doSPseed[cutIndex];
273  float BDTthreshold = getBDTthreshold(input.averageMu);
274  float bdt_score = dv->getDetail<float>("hitDV_bdt_score");
275 
276  if ( std::abs(seed_eta) < 1 ) {
277  BDTthreshold = getBDTthreshold_0eta1(input.averageMu, eff);
278  } else if ( std::abs(seed_eta) < 2 ) {
279  BDTthreshold = getBDTthreshold_1eta2(input.averageMu, eff);
280  }
281 
282  if( ! doSPseed && seed_type==SeedType::SP ) return false;
283  if( seed_type==SeedType::HLTJet && seed_pt < ptThreshold ) return false;
284  if( std::abs(seed_eta) > etaThreshold ) return false;
285  if( bdt_score < BDTthreshold ) return false;
286 
287  ATH_MSG_DEBUG( " Selected, cut index / seed_type / seed_eta / bdt_score = " << cutIndex << " / " << seed_type << " / " << seed_eta << " / " << bdt_score);
288 
289  return true;
290 }
291 
292 // ------------------------------------------------------------------------------------------------
293 // ------------------------------------------------------------------------------------------------
TrigHitDVHypoTool::m_cutJetEta
Gaudi::Property< std::vector< float > > m_cutJetEta
Definition: TrigHitDVHypoTool.h:58
PlotCalibFromCool.dv
dv
Definition: PlotCalibFromCool.py:762
TrigCompositeUtils::passed
bool passed(DecisionID id, const DecisionIDContainer &idSet)
checks if required decision ID is in the set of IDs in the container
Definition: TrigCompositeUtilsRoot.cxx:117
TrigCompositeUtils.h
HLT::Identifier::numeric
TrigCompositeUtils::DecisionID numeric() const
numeric ID
Definition: TrigCompositeUtils/TrigCompositeUtils/HLTIdentifier.h:47
TrigCompositeUtils::addDecisionID
void addDecisionID(DecisionID id, Decision *d)
Appends the decision (given as ID) to the decision object.
Definition: TrigCompositeUtilsRoot.cxx:61
TrigHitDVHypoTool::decide
StatusCode decide(std::vector< HitDVHypoInfo > &) const
decides upon a collection of tracks
Definition: TrigHitDVHypoTool.cxx:130
TrigHitDVHypoTool::multiplicitySelection
StatusCode multiplicitySelection(std::vector< HitDVHypoInfo > &) const
Definition: TrigHitDVHypoTool.cxx:189
TrigHitDVHypoTool::initialize
virtual StatusCode initialize() override
Definition: TrigHitDVHypoTool.cxx:30
TrigHitDVHypoTool::getBDTthreshold
float getBDTthreshold(float) const
Definition: TrigHitDVHypoTool.cxx:110
empty
bool empty(TH1 *h)
Definition: computils.cxx:294
TrigHitDVHypoTool::HitDVHypoInfo
Definition: TrigHitDVHypoTool.h:35
HLT
It used to be useful piece of code for replacing actual SG with other store of similar functionality ...
Definition: HLTResultReader.h:26
lumiFormat.i
int i
Definition: lumiFormat.py:85
EL::StatusCode
::StatusCode StatusCode
StatusCode definition for legacy code.
Definition: PhysicsAnalysis/D3PDTools/EventLoop/EventLoop/StatusCode.h:22
ATH_MSG_DEBUG
#define ATH_MSG_DEBUG(x)
Definition: AthMsgStreamMacros.h:29
PlotPulseshapeFromCool.input
input
Definition: PlotPulseshapeFromCool.py:106
test_pyathena.parent
parent
Definition: test_pyathena.py:15
TrigHitDVHypoTool::m_decisionId
HLT::Identifier m_decisionId
Definition: TrigHitDVHypoTool.h:56
TrigHitDVHypoTool.h
xAOD::TrigComposite_v1
Class used to describe composite objects in the HLT.
Definition: TrigComposite_v1.h:52
DeMoUpdate.tmp
string tmp
Definition: DeMoUpdate.py:1167
TrigHitDVHypoTool::inclusiveSelection
StatusCode inclusiveSelection(std::vector< HitDVHypoInfo > &) const
Definition: TrigHitDVHypoTool.cxx:152
HLT::elementsInUniqueCombinations
void elementsInUniqueCombinations(const Index2DVec &indices, std::set< size_t > &participants, std::function< bool(const Index1DVec &)> &&filter)
Definition: Combinators.cxx:154
TrigHitDVHypoTool::m_doSPseed
Gaudi::Property< std::vector< bool > > m_doSPseed
Definition: TrigHitDVHypoTool.h:60
name
std::string name
Definition: Control/AthContainers/Root/debug.cxx:221
createCoolChannelIdFile.par
par
Definition: createCoolChannelIdFile.py:29
TrigHitDVHypoTool::~TrigHitDVHypoTool
virtual ~TrigHitDVHypoTool()
Definition: TrigHitDVHypoTool.cxx:25
TrigHitDVHypoTool::getBDTthreshold_0eta1
float getBDTthreshold_0eta1(float, float) const
Definition: TrigHitDVHypoTool.cxx:46
Combinators.h
TrigHitDVHypoTool::m_effBDT
Gaudi::Property< std::vector< float > > m_effBDT
Definition: TrigHitDVHypoTool.h:59
TrigHitDVHypoTool::getBDTthreshold_1eta2
float getBDTthreshold_1eta2(float, float) const
Definition: TrigHitDVHypoTool.cxx:78
python.CaloScaleNoiseConfig.type
type
Definition: CaloScaleNoiseConfig.py:78
TrigHitDVHypoTool::TrigHitDVHypoTool
TrigHitDVHypoTool(const std::string &type, const std::string &name, const IInterface *parent)
Definition: TrigHitDVHypoTool.cxx:19
HLTIdentifier.h
LArNewCalib_DelayDump_OFC_Cali.idx
idx
Definition: LArNewCalib_DelayDump_OFC_Cali.py:69
TrigCompositeUtils
Definition: Event/xAOD/xAODTrigger/xAODTrigger/TrigComposite.h:19
HLT::Index2DVec
std::vector< Index1DVec > Index2DVec
Definition: TrigCompositeUtils/TrigCompositeUtils/Combinators.h:140
dqt_zlumi_alleff_HIST.eff
int eff
Definition: dqt_zlumi_alleff_HIST.py:113
AthAlgTool
Definition: AthAlgTool.h:26
TrigHitDVHypoTool::decideOnSingleObject
bool decideOnSingleObject(HitDVHypoInfo &, size_t, bool) const
Definition: TrigHitDVHypoTool.cxx:249
CaloNoise_fillDB.mu
mu
Definition: CaloNoise_fillDB.py:53
TrigHitDVHypoTool::m_cutJetPtGeV
Gaudi::Property< std::vector< float > > m_cutJetPtGeV
Definition: TrigHitDVHypoTool.h:57
Identifier
Definition: IdentifierFieldParser.cxx:14