]>
Commit | Line | Data |
---|---|---|
3c74311e | 1 | /************************************************************************** |
2 | * Copyright(c) 1998-2007, ALICE Experiment at CERN, All rights reserved. * | |
3 | * * | |
4 | * Author: The ALICE Off-line Project. * | |
5 | * Contributors are mentioned in the code where appropriate. * | |
6 | * * | |
7 | * Permission to use, copy, modify and distribute this software and its * | |
8 | * documentation strictly for non-commercial purposes is hereby granted * | |
9 | * without fee, provided that the above copyright notice appears in all * | |
10 | * copies and that both the copyright notice and this permission notice * | |
11 | * appear in the supporting documentation. The authors make no claims * | |
12 | * about the suitability of this software for any purpose. It is * | |
13 | * provided "as is" without express or implied warranty. * | |
14 | **************************************************************************/ | |
15 | ||
16 | //----------------------------------------------------------------------------- | |
17 | /// \class AliAnalysisTaskMuonPerformance | |
18 | /// Analysis task to chek the tracker and trigger reconstruction | |
19 | /// The output is a list of histograms. | |
20 | /// | |
21 | /// \author Diego Stocco and Philippe Pillot | |
22 | //----------------------------------------------------------------------------- | |
23 | ||
24 | // ROOT includes | |
25 | #include "TROOT.h" | |
26 | #include "TH1.h" | |
27 | #include "TH2.h" | |
28 | #include "TH3.h" | |
29 | #include "TF1.h" | |
30 | #include "TLegend.h" | |
31 | #include "TGraphErrors.h" | |
32 | #include "TGraphAsymmErrors.h" | |
33 | #include "TAxis.h" | |
34 | #include "TObjArray.h" | |
35 | #include "TCanvas.h" | |
36 | #include "TMath.h" | |
37 | #include "TMCProcess.h" | |
38 | #include "TGeoManager.h" | |
39 | ||
40 | // STEER includes | |
41 | #include "AliMCEvent.h" | |
42 | #include "AliMCParticle.h" | |
43 | #include "AliMCEventHandler.h" | |
44 | #include "AliESDEvent.h" | |
45 | #include "AliESDMuonTrack.h" | |
46 | #include "AliCDBManager.h" | |
47 | #include "AliGeomManager.h" | |
48 | ||
49 | // ANALYSIS includes | |
50 | #include "AliAnalysisManager.h" | |
51 | #include "AliAnalysisDataSlot.h" | |
52 | #include "AliAnalysisDataContainer.h" | |
53 | ||
54 | // CORRFW includes | |
55 | #include "AliCFContainer.h" | |
56 | #include "AliCFGridSparse.h" | |
57 | #include "AliCFEffGrid.h" | |
58 | ||
59 | // MUON includes | |
60 | #include "AliMUONConstants.h" | |
61 | #include "AliMUONTrack.h" | |
62 | #include "AliMUONTriggerTrack.h" | |
63 | #include "AliMUONLocalTrigger.h" | |
64 | #include "AliMUONVTrackStore.h" | |
65 | #include "AliMUONVTriggerTrackStore.h" | |
66 | #include "AliMUONESDInterface.h" | |
67 | #include "AliMUONRecoParam.h" | |
68 | #include "AliMUONCDB.h" | |
69 | #include "AliMUONTrackExtrap.h" | |
70 | #include "AliMUONTrackParam.h" | |
71 | #include "AliMUONRecoCheck.h" | |
72 | #include "AliMUONVCluster.h" | |
73 | #include "AliMpDEIterator.h" | |
74 | ||
75 | #include "AliAnalysisTaskMuonPerformance.h" | |
76 | ||
77 | ||
78 | /// \cond CLASSIMP | |
79 | ClassImp(AliAnalysisTaskMuonPerformance) // Class implementation in ROOT context | |
80 | /// \endcond | |
81 | ||
82 | ||
83 | //________________________________________________________________________ | |
84 | AliAnalysisTaskMuonPerformance::AliAnalysisTaskMuonPerformance() : | |
85 | AliAnalysisTaskSE(), | |
86 | fDefaultStorage(""), | |
87 | fNPBins(30), | |
88 | fCorrectForSystematics(kFALSE), | |
89 | fFitResiduals(kFALSE), | |
90 | fRequestedStationMask(0), | |
91 | fRequest2ChInSameSt45(0), | |
92 | fSigmaCut(-1.), | |
93 | fSigmaCutTrig(-1.), | |
94 | fNDE(0), | |
95 | fCFContainer(0x0), | |
96 | fEfficiencyList(0x0), | |
97 | fTriggerList(0x0), | |
98 | fTrackerList(0x0), | |
99 | fPAtVtxList(0x0), | |
100 | fSlopeAtVtxList(0x0), | |
101 | fEtaAtVtxList(0x0), | |
102 | fPhiAtVtxList(0x0), | |
103 | fPAt1stClList(0x0), | |
104 | fSlopeAt1stClList(0x0), | |
105 | fDCAList(0x0), | |
106 | fClusterList(0x0) | |
107 | { | |
108 | // | |
109 | /// Default Constructor. | |
110 | // | |
09c18f72 | 111 | fPRange[0] = 0.; |
112 | fPRange[1] = 0.; | |
113 | fClusterMaxRes[0] = 0.; | |
114 | fClusterMaxRes[1] = 0.; | |
115 | for (Int_t i = 0; i < 1100; i++) fDEIndices[i] = 0; | |
116 | for (Int_t i = 0; i < 200; i++) fDEIds[i] = 0; | |
3c74311e | 117 | } |
118 | ||
119 | ||
120 | //________________________________________________________________________ | |
121 | AliAnalysisTaskMuonPerformance::AliAnalysisTaskMuonPerformance(const char *name) : | |
122 | AliAnalysisTaskSE(name), | |
123 | fDefaultStorage("raw://"), | |
124 | fNPBins(30), | |
125 | fCorrectForSystematics(kFALSE), | |
126 | fFitResiduals(kFALSE), | |
127 | fRequestedStationMask(0), | |
128 | fRequest2ChInSameSt45(0), | |
129 | fSigmaCut(-1.), | |
130 | fSigmaCutTrig(-1.), | |
131 | fNDE(0), | |
132 | fCFContainer(0x0), | |
133 | fEfficiencyList(0x0), | |
134 | fTriggerList(0x0), | |
135 | fTrackerList(0x0), | |
136 | fPAtVtxList(0x0), | |
137 | fSlopeAtVtxList(0x0), | |
138 | fEtaAtVtxList(0x0), | |
139 | fPhiAtVtxList(0x0), | |
140 | fPAt1stClList(0x0), | |
141 | fSlopeAt1stClList(0x0), | |
142 | fDCAList(0x0), | |
143 | fClusterList(0x0) | |
144 | { | |
145 | // | |
146 | /// Constructor. | |
147 | // | |
148 | fPRange[0] = 0.; | |
149 | fPRange[1] = 300.; | |
150 | fClusterMaxRes[0] = 0.; | |
151 | fClusterMaxRes[1] = 0.; | |
09c18f72 | 152 | for (Int_t i = 0; i < 1100; i++) fDEIndices[i] = 0; |
153 | for (Int_t i = 0; i < 200; i++) fDEIds[i] = 0; | |
3c74311e | 154 | |
155 | DefineOutput(1, AliCFContainer::Class()); | |
156 | DefineOutput(2, TObjArray::Class()); | |
157 | DefineOutput(3, TObjArray::Class()); | |
158 | DefineOutput(4, TObjArray::Class()); | |
159 | DefineOutput(5, TObjArray::Class()); | |
160 | DefineOutput(6, TObjArray::Class()); | |
161 | DefineOutput(7, TObjArray::Class()); | |
162 | DefineOutput(8, TObjArray::Class()); | |
163 | DefineOutput(9, TObjArray::Class()); | |
164 | DefineOutput(10, TObjArray::Class()); | |
165 | DefineOutput(11, TObjArray::Class()); | |
166 | DefineOutput(12, TObjArray::Class()); | |
167 | } | |
168 | ||
169 | ||
170 | //________________________________________________________________________ | |
171 | AliAnalysisTaskMuonPerformance::~AliAnalysisTaskMuonPerformance() | |
172 | { | |
173 | // | |
174 | /// Destructor | |
175 | // | |
176 | if (!AliAnalysisManager::GetAnalysisManager()->IsProofMode()) { | |
177 | delete fCFContainer; | |
178 | delete fEfficiencyList; | |
179 | delete fTriggerList; | |
180 | delete fTrackerList; | |
181 | delete fPAtVtxList; | |
182 | delete fSlopeAtVtxList; | |
183 | delete fEtaAtVtxList; | |
184 | delete fPhiAtVtxList; | |
185 | delete fPAt1stClList; | |
186 | delete fSlopeAt1stClList; | |
187 | delete fDCAList; | |
188 | delete fClusterList; | |
189 | } | |
190 | } | |
191 | ||
192 | ||
193 | //___________________________________________________________________________ | |
194 | void AliAnalysisTaskMuonPerformance::NotifyRun() | |
195 | { | |
196 | // | |
197 | /// Use the event handler information to correctly fill the analysis flags: | |
198 | /// - check if Monte Carlo information is present | |
199 | // | |
200 | ||
201 | // load OCDB objects only once | |
202 | if (fSigmaCut > 0) return; | |
203 | ||
204 | // set OCDB location | |
205 | AliCDBManager* cdbm = AliCDBManager::Instance(); | |
206 | cdbm->SetDefaultStorage(fDefaultStorage.Data()); | |
207 | cdbm->SetRun(fCurrentRunNumber); | |
208 | ||
209 | // load magnetic field for track extrapolation | |
210 | if (!AliMUONCDB::LoadField()) return; | |
211 | ||
212 | // load mapping | |
213 | if (!AliMUONCDB::LoadMapping()) return; | |
214 | ||
215 | // load geometry for track extrapolation to vertex | |
216 | if (!AliGeomManager::GetGeometry()) AliGeomManager::LoadGeometry(); | |
217 | if (!AliGeomManager::GetGeometry()) return; | |
218 | ||
219 | // load recoParam | |
220 | AliMUONRecoParam* recoParam = AliMUONCDB::LoadRecoParam(); | |
221 | if (!recoParam) { | |
222 | fRequestedStationMask = 0; | |
223 | fRequest2ChInSameSt45 = kFALSE; | |
224 | fSigmaCut = -1.; | |
225 | fSigmaCutTrig = -1.; | |
226 | AliError("--> skip this run"); | |
227 | return; | |
228 | } | |
229 | ||
230 | // compute the mask of requested stations from recoParam | |
231 | fRequestedStationMask = 0; | |
232 | for (Int_t i = 0; i < 5; i++) if (recoParam->RequestStation(i)) fRequestedStationMask |= ( 1 << i ); | |
233 | ||
234 | // get from recoParam whether a track need 2 chambers hit in the same station (4 or 5) or not to be reconstructible | |
235 | fRequest2ChInSameSt45 = !recoParam->MakeMoreTrackCandidates(); | |
236 | ||
237 | // get sigma cut from recoParam to associate clusters with TrackRefs in case the labels are not used | |
238 | fSigmaCut = (recoParam->ImproveTracks()) ? recoParam->GetSigmaCutForImprovement() : recoParam->GetSigmaCutForTracking(); | |
239 | ||
240 | // get sigma cut from recoParam to associate trigger track to triggerable track | |
241 | fSigmaCutTrig = recoParam->GetSigmaCutForTrigger(); | |
242 | ||
243 | AliMUONESDInterface::ResetTracker(recoParam); | |
244 | ||
245 | for (Int_t i = 0; i < AliMUONConstants::NTrackingCh(); i++) { | |
246 | ||
247 | // find the highest chamber resolution and set histogram bins | |
248 | if (recoParam->GetDefaultNonBendingReso(i) > fClusterMaxRes[0]) fClusterMaxRes[0] = recoParam->GetDefaultNonBendingReso(i); | |
249 | if (recoParam->GetDefaultBendingReso(i) > fClusterMaxRes[1]) fClusterMaxRes[1] = recoParam->GetDefaultBendingReso(i); | |
250 | ||
251 | // fill correspondence between DEId and indices for histo (starting from 1) | |
252 | AliMpDEIterator it; | |
253 | it.First(i); | |
254 | while (!it.IsDone()) { | |
255 | fNDE++; | |
256 | fDEIndices[it.CurrentDEId()] = fNDE; | |
257 | fDEIds[fNDE] = it.CurrentDEId(); | |
258 | it.Next(); | |
259 | } | |
260 | ||
261 | } | |
262 | ||
263 | UserCreateOutputObjects(); | |
264 | } | |
265 | ||
266 | ||
267 | //___________________________________________________________________________ | |
268 | void AliAnalysisTaskMuonPerformance::UserCreateOutputObjects() | |
269 | { | |
270 | // | |
271 | /// Create output objects | |
272 | // | |
273 | ||
274 | // do it once the OCDB has been loaded (i.e. from NotifyRun()) | |
275 | if (fSigmaCut < 0) return; | |
276 | ||
277 | // ------ CFContainer ------ | |
278 | ||
279 | // define axes of particle container | |
280 | Int_t nPtBins = 60; | |
281 | Double_t ptMin = 0., ptMax = 30.; | |
282 | TString ptName("Pt"), ptTitle("p_{t}"), ptUnits("GeV/c"); | |
283 | ||
284 | Int_t nEtaBins = 25; | |
285 | Double_t etaMin = -4.5, etaMax = -2.; | |
286 | TString etaName("Eta"), etaTitle("#eta"), etaUnits("a.u."); | |
287 | ||
288 | Int_t nPhiBins = 36; | |
289 | Double_t phiMin = 0.; Double_t phiMax = 2*TMath::Pi(); | |
290 | TString phiName("Phi"), phiTitle("#phi"), phiUnits("rad"); | |
291 | ||
292 | Int_t nThetaAbsEndBins = 4; | |
293 | Double_t thetaAbsEndMin = -0.5, thetaAbsEndMax = 3.5; | |
294 | TString thetaAbsEndName("ThetaAbsEnd"), thetaAbsEndTitle("#theta_{abs}"), thetaAbsEndUnits("a.u."); | |
295 | ||
296 | Int_t nChargeBins = 2; | |
297 | Double_t chargeMin = -2, chargeMax = 2.; | |
298 | TString chargeName("Charge"), chargeTitle("charge"), chargeUnits("e"); | |
299 | ||
300 | Int_t nHasTrackerBins = 2; | |
301 | Double_t hasTrackerMin = -0.5, hasTrackerMax = (Double_t)nHasTrackerBins - 0.5; | |
302 | TString hasTrackerName("HasTracker"), hasTrackerTitle("Has tracker"), hasTrackerUnits(""); | |
303 | ||
304 | Int_t nTriggerBins = kNtrigCuts; | |
305 | Double_t triggerMin = -0.5, triggerMax = (Double_t)nTriggerBins - 0.5; | |
306 | TString triggerName("MatchTrig"), triggerTitle("Trigger match"), triggerUnits(""); | |
307 | ||
308 | Int_t nMotherTypeBins = kNtrackSources; | |
309 | Double_t motherTypeMin = -0.5, motherTypeMax = (Double_t)kNtrackSources - 0.5; | |
310 | TString motherTypeName("MotherType"), motherTypeTitle("motherType"), motherTypeUnits(""); | |
311 | ||
312 | Int_t nMatchMCBins = kNMatchMC; | |
313 | Double_t matchMCMin = -0.5, matchMCMax = (Double_t)kNMatchMC - 0.5; | |
314 | TString matchMCName("MatchMC"), matchMCTitle("MatchMC"), matchMCUnits(""); | |
315 | ||
316 | Int_t nbins[kNvars] = {nPtBins, nEtaBins, nPhiBins, nThetaAbsEndBins, nChargeBins, nHasTrackerBins, nTriggerBins, nMotherTypeBins, nMatchMCBins}; | |
317 | Double_t xmin[kNvars] = {ptMin, etaMin, phiMin, thetaAbsEndMin, chargeMin, hasTrackerMin, triggerMin, motherTypeMin, matchMCMin}; | |
318 | Double_t xmax[kNvars] = {ptMax, etaMax, phiMax, thetaAbsEndMax, chargeMax, hasTrackerMax, triggerMax, motherTypeMax, matchMCMax}; | |
319 | TString axisTitle[kNvars] = {ptTitle, etaTitle, phiTitle, thetaAbsEndTitle, chargeTitle, hasTrackerTitle, triggerTitle, motherTypeTitle, matchMCTitle}; | |
320 | TString axisUnits[kNvars] = {ptUnits, etaUnits, phiUnits, thetaAbsEndUnits, chargeUnits, hasTrackerUnits, triggerUnits, motherTypeUnits, matchMCUnits}; | |
321 | ||
322 | // create particle container | |
323 | fCFContainer = new AliCFContainer(GetOutputSlot(1)->GetContainer()->GetName(),"container for tracks",kNsteps,kNvars,nbins); | |
324 | ||
325 | // set axes title and limits | |
326 | for ( Int_t idim = 0; idim<kNvars; idim++) { | |
327 | TString histoTitle = Form("%s (%s)", axisTitle[idim].Data(), axisUnits[idim].Data()); | |
328 | histoTitle.ReplaceAll("()",""); | |
329 | fCFContainer->SetVarTitle(idim, histoTitle.Data()); | |
330 | fCFContainer->SetBinLimits(idim, xmin[idim], xmax[idim]); | |
331 | } | |
332 | ||
333 | // define histo names | |
334 | TString stepTitle[kNsteps] = {"reconstructed", "generated"}; | |
335 | ||
336 | // define axes labels if any | |
337 | TString trigName[kNtrigCuts]; | |
338 | trigName[kNoMatchTrig] = "NoMatch"; | |
339 | trigName[kAllPtTrig] = "AllPt"; | |
340 | trigName[kLowPtTrig] = "LowPt"; | |
341 | trigName[kHighPtTrig] = "HighPt"; | |
342 | ||
343 | TString srcName[kNtrackSources]; | |
344 | srcName[kCharmMu] = "Charm"; | |
345 | srcName[kBeautyMu] = "Beauty"; | |
346 | srcName[kPrimaryMu] = "Decay"; | |
347 | srcName[kSecondaryMu] = "Secondary"; | |
348 | srcName[kRecoHadron] = "Hadrons"; | |
349 | srcName[kUnknownPart] = "Fakes"; | |
350 | ||
351 | TString mMCName[kNMatchMC]; | |
352 | mMCName[kNoMatch] = "NoMatch"; | |
353 | mMCName[kTrackerOnly] = "TrackerOnly"; | |
354 | mMCName[kMatchedSame] = "MatchedSame"; | |
355 | mMCName[kMatchedDiff] = "MatchedDiff"; | |
356 | mMCName[kTriggerOnly] = "TriggerOnly"; | |
357 | ||
358 | // set histo name and axis labels if any | |
359 | for (Int_t istep=0; istep<kNsteps; istep++) { | |
360 | ||
361 | // histo name | |
362 | fCFContainer->SetStepTitle(istep, stepTitle[istep].Data()); | |
363 | AliCFGridSparse* gridSparse = fCFContainer->GetGrid(istep); | |
364 | ||
365 | // trigger info | |
366 | TAxis* triggerAxis = gridSparse->GetAxis(kVarTrigger); | |
367 | for ( Int_t ibin=0; ibin<kNtrigCuts; ibin++ ) { | |
368 | triggerAxis->SetBinLabel(ibin+1,trigName[ibin]); | |
369 | } | |
370 | ||
371 | // mother type | |
372 | TAxis* motherTypeAxis = gridSparse->GetAxis(kVarMotherType); | |
373 | for ( Int_t ibin=0; ibin<kNtrackSources; ibin++ ) { | |
374 | motherTypeAxis->SetBinLabel(ibin+1,srcName[ibin]); | |
375 | } | |
376 | ||
377 | // MC matching flag | |
378 | TAxis* matchMCAxis = gridSparse->GetAxis(kVarMatchMC); | |
379 | for ( Int_t ibin=0; ibin<kNMatchMC; ibin++ ) { | |
380 | matchMCAxis->SetBinLabel(ibin+1,mMCName[ibin]); | |
381 | } | |
382 | ||
383 | } | |
384 | ||
385 | // ------ trigger histograms ------ | |
386 | ||
387 | fTriggerList = new TObjArray(100); | |
388 | fTriggerList->SetOwner(); | |
389 | ||
390 | TH1F* h1 = new TH1F("hResTrigX11", "Residual X11;X11_{reco} - X11_{MC} (cm)", 100, -10., 10.); | |
391 | fTriggerList->AddAt(h1, kResTrigX11); | |
392 | h1 = new TH1F("hResTrigY11", "Residual Y11;Y11_{reco} - Y11_{MC} (cm)", 100, -10., 10.); | |
393 | fTriggerList->AddAt(h1, kResTrigY11); | |
394 | h1 = new TH1F("hResTrigSlopeY", "Residual slope y;ySlope_{reco} - ySlope_{MC} (rad)", 100, -0.1, 0.1); | |
395 | fTriggerList->AddAt(h1, kResTrigSlopeY); | |
396 | ||
397 | // ------ tracker histograms ------ | |
398 | ||
399 | fTrackerList = new TObjArray(100); | |
400 | fTrackerList->SetOwner(); | |
401 | ||
402 | // momentum resolution at vertex | |
403 | const Int_t deltaPAtVtxNBins = 250; | |
404 | Double_t deltaPAtVtxEdges[2]; | |
405 | deltaPAtVtxEdges[0] = -20. - 0.05 * fPRange[1]; | |
406 | deltaPAtVtxEdges[1] = 5. + 0.05 * fPRange[1]; | |
407 | ||
408 | h1 = new TH1F("hResPAtVtx"," delta P at vertex;#Delta_{p} (GeV/c)",deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
409 | fTrackerList->AddAt(h1, kResPAtVtx); | |
410 | TH2F *h2 = new TH2F("hResPAtVtxVsP","#Delta_{p} at vertex versus p;p (GeV/c);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
411 | fTrackerList->AddAt(h2, kResPAtVtxVsP); | |
412 | h2 = new TH2F("hResPAtVtxVsPIn23deg","#Delta_{p} at vertex versus p for tracks between 2 and 3 degrees at absorber end;p (GeV/c);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
413 | fTrackerList->AddAt(h2, kResPAtVtxVsPIn23deg); | |
414 | h2 = new TH2F("hResPAtVtxVsPIn310deg","#Delta_{p} at vertex versus p for tracks between 3 and 10 degrees at absorber end;p (GeV/c);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
415 | fTrackerList->AddAt(h2, kResPAtVtxVsPIn310deg); | |
416 | h2 = new TH2F("hResPAtVtxVsPIn02degMC","#Delta_{p} at vertex versus p for tracks with MC angle below 2 degrees;p (GeV/c);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],deltaPAtVtxNBins/10,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
417 | fTrackerList->AddAt(h2, kResPAtVtxVsPIn02degMC); | |
418 | h2 = new TH2F("hResPAtVtxVsPosAbsEndIn02degMC","#Delta_{p} at vertex versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);#Delta_{p} (GeV/c)",1000,0.,100.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
419 | fTrackerList->AddAt(h2, kResPAtVtxVsPosAbsEndIn02degMC); | |
420 | h2 = new TH2F("hResPAtVtxVsPosAbsEndIn23degMC","#Delta_{p} at vertex versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);#Delta_{p} (GeV/c)",1000,0.,100.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
421 | fTrackerList->AddAt(h2, kResPAtVtxVsPosAbsEndIn23degMC); | |
422 | h2 = new TH2F("hResPAtVtxVsPosAbsEndIn310degMC","#Delta_{p} at vertex versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);#Delta_{p} (GeV/c)",1000,0.,100.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
423 | fTrackerList->AddAt(h2, kResPAtVtxVsPosAbsEndIn310degMC); | |
424 | h2 = new TH2F("hResPAtVtxVsAngleAtAbsEnd","#Delta_{p} at vertex versus track position at absorber end converted to degrees;angle (Deg);#Delta_{p} (GeV/c)",10,0.,10.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
425 | fTrackerList->AddAt(h2, kResPAtVtxVsAngleAtAbsEnd); | |
426 | h2 = new TH2F("hResPAtVtxVsMCAngle","#Delta_{p} at vertex versus MC angle;MC angle (Deg);#Delta_{p} (GeV/c)",10,0.,10.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
427 | fTrackerList->AddAt(h2, kResPAtVtxVsMCAngle); | |
428 | TH3F *h3 = new TH3F("hResPAtVtxVsAngleAtAbsEndVsP","#Delta_{p} at vertex versus track position at absorber end converted to degrees versus momentum;p (GeV/c);angle (Deg);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],100,0.,10.,deltaPAtVtxNBins,deltaPAtVtxEdges[0],deltaPAtVtxEdges[1]); | |
429 | fTrackerList->AddAt(h3, kResPAtVtxVsAngleAtAbsEndVsP); | |
430 | ||
431 | // transverse momentum resolution at vertex | |
432 | h2 = new TH2F("hResPtAtVtxVsPt","#Delta_{p_{t}} at vertex versus p_{t};p_{t} (GeV/c);#Delta_{p_{t}} (GeV/c)",2*fNPBins,fPRange[0]/10.,fPRange[1]/10.,deltaPAtVtxNBins,deltaPAtVtxEdges[0]/10.,deltaPAtVtxEdges[1]/10.); | |
433 | fTrackerList->AddAt(h2, kResPtAtVtxVsPt); | |
434 | ||
435 | // momentum resolution at first cluster | |
436 | const Int_t deltaPAtFirstClNBins = 500; | |
437 | Double_t deltaPAtFirstClEdges[2]; | |
438 | deltaPAtFirstClEdges[0] = -5. - 0.05 * fPRange[1]; | |
439 | deltaPAtFirstClEdges[1] = 5. + 0.05 * fPRange[1]; | |
440 | ||
441 | h1 = new TH1F("hResPAt1stCl"," delta P at first cluster;#Delta_{p} (GeV/c)",deltaPAtFirstClNBins,deltaPAtFirstClEdges[0],deltaPAtFirstClEdges[1]); | |
442 | fTrackerList->AddAt(h1, kResPAt1stCl); | |
443 | h2 = new TH2F("hResPAt1stClVsP","#Delta_{p} at first cluster versus p;p (GeV/c);#Delta_{p} (GeV/c)",2*fNPBins,fPRange[0],fPRange[1],deltaPAtFirstClNBins,deltaPAtFirstClEdges[0],deltaPAtFirstClEdges[1]); | |
444 | fTrackerList->AddAt(h2, kResPAt1stClVsP); | |
445 | ||
446 | // transverse momentum resolution at vertex | |
447 | h2 = new TH2F("hResPtAt1stClVsPt","#Delta_{p_{t}} at first cluster versus p_{t};p_{t} (GeV/c);#Delta_{p_{t}} (GeV/c)",2*fNPBins,fPRange[0]/10.,fPRange[1]/10.,deltaPAtFirstClNBins,deltaPAtFirstClEdges[0]/10.,deltaPAtFirstClEdges[1]/10.); | |
448 | fTrackerList->AddAt(h2, kResPtAt1stClVsPt); | |
449 | ||
450 | // angular resolution at vertex | |
451 | const Int_t deltaSlopeAtVtxNBins = 500; | |
452 | const Double_t deltaSlopeAtVtxEdges[2] = {-0.05, 0.05}; | |
453 | ||
454 | h1 = new TH1F("hResSlopeXAtVtx","#Delta_{slope_{X}} at vertex;#Delta_{slope_{X}}", deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
455 | fTrackerList->AddAt(h1, kResSlopeXAtVtx); | |
456 | h1 = new TH1F("hResSlopeYAtVtx","#Delta_{slope_{Y}} at vertex;#Delta_{slope_{Y}}", deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
457 | fTrackerList->AddAt(h1, kResSlopeYAtVtx); | |
458 | h2 = new TH2F("hResSlopeXAtVtxVsP","#Delta_{slope_{X}} at vertex versus p;p (GeV/c);#Delta_{slope_{X}}",2*fNPBins,fPRange[0],fPRange[1], deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
459 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsP); | |
460 | h2 = new TH2F("hResSlopeYAtVtxVsP","#Delta_{slope_{Y}} at vertex versus p;p (GeV/c);#Delta_{slope_{Y}}",2*fNPBins,fPRange[0],fPRange[1], deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
461 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsP); | |
462 | h2 = new TH2F("hResSlopeXAtVtxVsPosAbsEndIn02degMC","#Delta_{slope_{X}} at vertex versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);#Delta_{slope_{X}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
463 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsPosAbsEndIn02degMC); | |
464 | h2 = new TH2F("hResSlopeYAtVtxVsPosAbsEndIn02degMC","#Delta_{slope_{Y}} at vertex versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);#Delta_{slope_{Y}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
465 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsPosAbsEndIn02degMC); | |
466 | h2 = new TH2F("hResSlopeXAtVtxVsPosAbsEndIn23degMC","#Delta_{slope_{X}} at vertex versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);#Delta_{slope_{X}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
467 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsPosAbsEndIn23degMC); | |
468 | h2 = new TH2F("hResSlopeYAtVtxVsPosAbsEndIn23degMC","#Delta_{slope_{Y}} at vertex versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);#Delta_{slope_{Y}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
469 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsPosAbsEndIn23degMC); | |
470 | h2 = new TH2F("hResSlopeXAtVtxVsPosAbsEndIn310degMC","#Delta_{slope_{X}} at vertex versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);#Delta_{slope_{X}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
471 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsPosAbsEndIn310degMC); | |
472 | h2 = new TH2F("hResSlopeYAtVtxVsPosAbsEndIn310degMC","#Delta_{slope_{Y}} at vertex versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);#Delta_{slope_{Y}}",1000,0.,100.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
473 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsPosAbsEndIn310degMC); | |
474 | h2 = new TH2F("hResSlopeXAtVtxVsAngleAtAbsEnd","#Delta_{slope_{X}} at vertex versus track position at absorber end converted to degrees;angle (Deg);#Delta_{slope_{X}}",10,0.,10.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
475 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsAngleAtAbsEnd); | |
476 | h2 = new TH2F("hResSlopeYAtVtxVsAngleAtAbsEnd","#Delta_{slope_{Y}} at vertex versus track position at absorber end converted to degrees;angle (Deg);#Delta_{slope_{Y}}",10,0.,10.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
477 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsAngleAtAbsEnd); | |
478 | h2 = new TH2F("hResSlopeXAtVtxVsMCAngle","#Delta_{slope_{X}} at vertex versus MC angle;MC angle (Deg);#Delta_{slope_{X}}",10,0.,10.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
479 | fTrackerList->AddAt(h2, kResSlopeXAtVtxVsMCAngle); | |
480 | h2 = new TH2F("hResSlopeYAtVtxVsMCAngle","#Delta_{slope_{Y}} at vertex versus MC angle;MC angle (Deg);#Delta_{slope_{Y}}",10,0.,10.,deltaSlopeAtVtxNBins, deltaSlopeAtVtxEdges[0], deltaSlopeAtVtxEdges[1]); | |
481 | fTrackerList->AddAt(h2, kResSlopeYAtVtxVsMCAngle); | |
482 | ||
483 | // angular resolution at first cluster | |
484 | const Int_t deltaSlopeAtFirstClNBins = 500; | |
485 | const Double_t deltaSlopeAtFirstClEdges[2] = {-0.01, 0.01}; | |
486 | ||
487 | h1 = new TH1F("hResSlopeXAt1stCl","#Delta_{slope_{X}} at first cluster;#Delta_{slope_{X}}", deltaSlopeAtFirstClNBins, deltaSlopeAtFirstClEdges[0], deltaSlopeAtFirstClEdges[1]); | |
488 | fTrackerList->AddAt(h1, kResSlopeXAt1stCl); | |
489 | h1 = new TH1F("hResSlopeYAt1stCl","#Delta_{slope_{Y}} at first cluster;#Delta_{slope_{Y}}", deltaSlopeAtFirstClNBins, deltaSlopeAtFirstClEdges[0], deltaSlopeAtFirstClEdges[1]); | |
490 | fTrackerList->AddAt(h1, kResSlopeYAt1stCl); | |
491 | h2 = new TH2F("hResSlopeXAt1stClVsP","#Delta_{slope_{X}} at first cluster versus p;p (GeV/c);#Delta_{slope_{X}}",2*fNPBins,fPRange[0],fPRange[1], deltaSlopeAtFirstClNBins, deltaSlopeAtFirstClEdges[0], deltaSlopeAtFirstClEdges[1]); | |
492 | fTrackerList->AddAt(h2, kResSlopeXAt1stClVsP); | |
493 | h2 = new TH2F("hResSlopeYAt1stClVsP","#Delta_{slope_{Y}} at first cluster versus p;p (GeV/c);#Delta_{slope_{Y}}",2*fNPBins,fPRange[0],fPRange[1], deltaSlopeAtFirstClNBins, deltaSlopeAtFirstClEdges[0], deltaSlopeAtFirstClEdges[1]); | |
494 | fTrackerList->AddAt(h2, kResSlopeYAt1stClVsP); | |
495 | ||
496 | // eta resolution at vertex | |
497 | const Int_t deltaEtaAtVtxNBins = 500; | |
498 | const Double_t deltaEtaAtVtxEdges[2] = {-0.5, 0.5}; | |
499 | ||
500 | h1 = new TH1F("hResEtaAtVtx","#Delta_{eta} at vertex;#Delta_{eta}", deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
501 | fTrackerList->AddAt(h1, kResEtaAtVtx); | |
502 | h2 = new TH2F("hResEtaAtVtxVsP","#Delta_{eta} at vertex versus p;p (GeV/c);#Delta_{eta}",2*fNPBins,fPRange[0],fPRange[1], deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
503 | fTrackerList->AddAt(h2, kResEtaAtVtxVsP); | |
504 | h2 = new TH2F("hResEtaAtVtxVsPosAbsEndIn02degMC","#Delta_{eta} at vertex versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);#Delta_{eta}",1000,0.,100.,deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
505 | fTrackerList->AddAt(h2, kResEtaAtVtxVsPosAbsEndIn02degMC); | |
506 | h2 = new TH2F("hResEtaAtVtxVsPosAbsEndIn23degMC","#Delta_{eta} at vertex versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);#Delta_{eta}",1000,0.,100.,deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
507 | fTrackerList->AddAt(h2, kResEtaAtVtxVsPosAbsEndIn23degMC); | |
508 | h2 = new TH2F("hResEtaAtVtxVsPosAbsEndIn310degMC","#Delta_{eta} at vertex versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);#Delta_{eta}",1000,0.,100.,deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
509 | fTrackerList->AddAt(h2, kResEtaAtVtxVsPosAbsEndIn310degMC); | |
510 | h2 = new TH2F("hResEtaAtVtxVsAngleAtAbsEnd","#Delta_{eta} at vertex versus track position at absorber end converted to degrees;angle (Deg);#Delta_{eta}",10,0.,10.,deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
511 | fTrackerList->AddAt(h2, kResEtaAtVtxVsAngleAtAbsEnd); | |
512 | h2 = new TH2F("hResEtaAtVtxVsMCAngle","#Delta_{eta} at vertex versus MC angle;MC angle (Deg);#Delta_{eta}",10,0.,10.,deltaEtaAtVtxNBins, deltaEtaAtVtxEdges[0], deltaEtaAtVtxEdges[1]); | |
513 | fTrackerList->AddAt(h2, kResEtaAtVtxVsMCAngle); | |
514 | ||
515 | // phi resolution at vertex | |
516 | const Int_t deltaPhiAtVtxNBins = 500; | |
517 | const Double_t deltaPhiAtVtxEdges[2] = {-0.5, 0.5}; | |
518 | ||
519 | h1 = new TH1F("hResPhiAtVtx","#Delta_{phi} at vertex;#Delta_{phi}", deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
520 | fTrackerList->AddAt(h1, kResPhiAtVtx); | |
521 | h2 = new TH2F("hResPhiAtVtxVsP","#Delta_{phi} at vertex versus p;p (GeV/c);#Delta_{phi}",2*fNPBins,fPRange[0],fPRange[1], deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
522 | fTrackerList->AddAt(h2, kResPhiAtVtxVsP); | |
523 | h2 = new TH2F("hResPhiAtVtxVsPosAbsEndIn02degMC","#Delta_{phi} at vertex versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);#Delta_{phi}",1000,0.,100.,deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
524 | fTrackerList->AddAt(h2, kResPhiAtVtxVsPosAbsEndIn02degMC); | |
525 | h2 = new TH2F("hResPhiAtVtxVsPosAbsEndIn23degMC","#Delta_{phi} at vertex versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);#Delta_{phi}",1000,0.,100.,deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
526 | fTrackerList->AddAt(h2, kResPhiAtVtxVsPosAbsEndIn23degMC); | |
527 | h2 = new TH2F("hResPhiAtVtxVsPosAbsEndIn310degMC","#Delta_{phi} at vertex versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);#Delta_{phi}",1000,0.,100.,deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
528 | fTrackerList->AddAt(h2, kResPhiAtVtxVsPosAbsEndIn310degMC); | |
529 | h2 = new TH2F("hResPhiAtVtxVsAngleAtAbsEnd","#Delta_{phi} at vertex versus track position at absorber end converted to degrees;angle (Deg);#Delta_{phi}",10,0.,10.,deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
530 | fTrackerList->AddAt(h2, kResPhiAtVtxVsAngleAtAbsEnd); | |
531 | h2 = new TH2F("hResPhiAtVtxVsMCAngle","#Delta_{phi} at vertex versus MC angle;MC angle (Deg);#Delta_{phi}",10,0.,10.,deltaPhiAtVtxNBins, deltaPhiAtVtxEdges[0], deltaPhiAtVtxEdges[1]); | |
532 | fTrackerList->AddAt(h2, kResPhiAtVtxVsMCAngle); | |
533 | ||
534 | // DCA resolution | |
535 | const Int_t deltaPDCANBins = 500; | |
536 | const Double_t deltaPDCAEdges[2] = {0., 1000.}; | |
537 | const Double_t deltaPMCSAngEdges[2] = {-1.5, 1.5}; | |
538 | ||
539 | h1 = new TH1F("hPDCA","p #times DCA at vertex;p #times DCA (GeV #times cm)", deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
540 | fTrackerList->AddAt(h1, kPDCA); | |
541 | h2 = new TH2F("hPDCAVsPIn23deg","p #times DCA versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);p #times DCA (GeV #times cm)",2*fNPBins,fPRange[0],fPRange[1], deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
542 | fTrackerList->AddAt(h2, kPDCAVsPIn23deg); | |
543 | h2 = new TH2F("hPDCAVsPIn310deg","p #times DCA versus p for tracks within [3,10[ degrees at absorber end;p (GeV/c);p #times DCA (GeV #times cm)",2*fNPBins,fPRange[0],fPRange[1], deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
544 | fTrackerList->AddAt(h2, kPDCAVsPIn310deg); | |
545 | h2 = new TH2F("hPDCAVsPosAbsEndIn02degMC","p #times DCA versus track position at absorber end for tracks with MC angle < 2 degrees;position (cm);p #times DCA (GeV #times cm)",1000,0.,100.,deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
546 | fTrackerList->AddAt(h2, kPDCAVsPosAbsEndIn02degMC); | |
547 | h2 = new TH2F("hPDCAVsPosAbsEndIn23degMC","p #times DCA}versus track position at absorber end for tracks with MC angle in [2,3[ degrees;position (cm);p #times DCA (GeV #times cm)",1000,0.,100.,deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
548 | fTrackerList->AddAt(h2, kPDCAVsPosAbsEndIn23degMC); | |
549 | h2 = new TH2F("hPDCAVsPosAbsEndIn310degMC","p #times DCA versus track position at absorber end for tracks with MC angle in [3,10[ degrees;position (cm);p #times DCA (GeV #times cm)",1000,0.,100.,deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
550 | fTrackerList->AddAt(h2, kPDCAVsPosAbsEndIn310degMC); | |
551 | h2 = new TH2F("hPDCAVsAngleAtAbsEnd","p #times DCA versus track position at absorber end converted to degrees;angle (Deg);p #times DCA (GeV #times cm)",10,0.,10.,deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
552 | fTrackerList->AddAt(h2, kPDCAVsAngleAtAbsEnd); | |
553 | h2 = new TH2F("hPDCAVsMCAngle","p #times DCA versus MC angle;MC angle (Deg);p #times DCA (GeV #times cm)",10,0.,10.,deltaPDCANBins, deltaPDCAEdges[0], deltaPDCAEdges[1]); | |
554 | fTrackerList->AddAt(h2, kPDCAVsMCAngle); | |
555 | ||
556 | // MCS angular dispersion | |
557 | h2 = new TH2F("hPMCSAngVsPIn23deg","p #times #Delta#theta_{MCS} versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);p #times #Delta#theta_{MCS} (GeV)",2*fNPBins,fPRange[0],fPRange[1], deltaPDCANBins, deltaPMCSAngEdges[0], deltaPMCSAngEdges[1]); | |
558 | fTrackerList->AddAt(h2, kPMCSAngVsPIn23deg); | |
559 | h2 = new TH2F("hPMCSAngVsPIn310deg","p #times #Delta#theta_{MCS} versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);p #times #Delta#theta_{MCS} (GeV)",2*fNPBins,fPRange[0],fPRange[1], deltaPDCANBins, deltaPMCSAngEdges[0], deltaPMCSAngEdges[1]); | |
560 | fTrackerList->AddAt(h2, kPMCSAngVsPIn310deg); | |
561 | ||
562 | // cluster resolution | |
563 | Int_t nCh = AliMUONConstants::NTrackingCh(); | |
564 | const Int_t clusterResNBins = 5000; | |
565 | Double_t clusterResMaxX = 10.*fClusterMaxRes[0]; | |
566 | Double_t clusterResMaxY = 10.*fClusterMaxRes[1]; | |
567 | ||
568 | h2 = new TH2F("hResClXVsCh", "cluster-track residual-X distribution per chamber;chamber ID;#Delta_{X} (cm)", nCh, 0.5, nCh+0.5, clusterResNBins, -clusterResMaxX, clusterResMaxX); | |
569 | fTrackerList->AddAt(h2, kResClXVsCh); | |
570 | h2 = new TH2F("hResClYVsCh", "cluster-track residual-Y distribution per chamber;chamber ID;#Delta_{Y} (cm)", nCh, 0.5, nCh+0.5, clusterResNBins, -clusterResMaxY, clusterResMaxY); | |
571 | fTrackerList->AddAt(h2, kResClYVsCh); | |
572 | h2 = new TH2F("hResClXVsDE", "cluster-track residual-X distribution per DE;DE ID;#Delta_{X} (cm)", fNDE, 0.5, fNDE+0.5, clusterResNBins, -clusterResMaxX, clusterResMaxX); | |
573 | for (Int_t i = 1; i <= fNDE; i++) h2->GetXaxis()->SetBinLabel(i, Form("%d",fDEIds[i])); | |
574 | fTrackerList->AddAt(h2, kResClXVsDE); | |
575 | h2 = new TH2F("hResClYVsDE", "cluster-track residual-Y distribution per DE;DE ID;#Delta_{Y} (cm)", fNDE, 0.5, fNDE+0.5, clusterResNBins, -clusterResMaxY, clusterResMaxY); | |
576 | for (Int_t i = 1; i <= fNDE; i++) h2->GetXaxis()->SetBinLabel(i, Form("%d",fDEIds[i])); | |
577 | fTrackerList->AddAt(h2, kResClYVsDE); | |
578 | ||
579 | // Disable printout of AliMCEvent | |
580 | AliLog::SetClassDebugLevel("AliMCEvent",-1); | |
581 | ||
582 | PostData(1, fCFContainer); | |
583 | PostData(3, fTriggerList); | |
584 | PostData(4, fTrackerList); | |
585 | } | |
586 | ||
587 | //________________________________________________________________________ | |
588 | void AliAnalysisTaskMuonPerformance::UserExec(Option_t * /*option*/) | |
589 | { | |
590 | // | |
591 | /// Main loop | |
592 | /// Called for each event | |
593 | // | |
594 | ||
595 | // check that OCDB objects have been properly set | |
596 | if (fSigmaCut < 0) return; | |
597 | ||
598 | // Load ESD event | |
599 | AliESDEvent* esd = dynamic_cast<AliESDEvent*>(InputEvent()); | |
600 | ||
601 | if ( ! esd ) { | |
602 | AliError ("ESD event not found. Nothing done!"); | |
603 | return; | |
604 | } | |
605 | ||
606 | // Load MC event | |
607 | AliMCEventHandler* mcH = static_cast<AliMCEventHandler*>(AliAnalysisManager::GetAnalysisManager()->GetMCtruthEventHandler()); | |
608 | if ( ! mcH ) { | |
609 | AliError ("MCH event handler not found. Nothing done!"); | |
610 | return; | |
611 | } | |
612 | ||
613 | // Get reference tracks | |
614 | AliMUONRecoCheck rc(esd,mcH); | |
615 | AliMUONVTriggerTrackStore* triggerTrackRefStore = rc.TriggerableTracks(-1); | |
616 | AliMUONVTrackStore* reconstructibleStore = rc.ReconstructibleTracks(-1, fRequestedStationMask, fRequest2ChInSameSt45); | |
617 | ||
618 | Double_t containerInput[kNvars]; | |
619 | AliMUONTrackParam *trackParam; | |
620 | Double_t x1,y1,z1,slopex1,slopey1,pX1,pY1,pZ1,p1,pT1,eta1,phi1; | |
621 | Double_t x2,y2,z2,slopex2,slopey2,pX2,pY2,pZ2,p2,pT2,eta2,phi2; | |
622 | Double_t dPhi; | |
623 | Double_t xAbs,yAbs,dAbs,aAbs,aMCS,aMC; | |
624 | Double_t xDCA,yDCA,dca,pU; | |
625 | ||
626 | // ------ Loop over reconstructed tracks ------ | |
627 | AliESDMuonTrack *esdTrack = 0x0; | |
628 | Int_t nMuTracks = esd->GetNumberOfMuonTracks(); | |
629 | for (Int_t iMuTrack = 0; iMuTrack < nMuTracks; ++iMuTrack) { | |
630 | ||
631 | esdTrack = esd->GetMuonTrack(iMuTrack); | |
632 | ||
633 | AliMUONTrack* matchedTrackRef = 0x0; | |
634 | AliMUONTriggerTrack* matchedTrigTrackRef = 0x0; | |
635 | containerInput[kVarMatchMC] = static_cast<Double_t>(kNoMatch); | |
636 | ||
637 | // Tracker | |
638 | if (esdTrack->ContainTrackerData()) { | |
639 | ||
640 | // convert ESD track to MUON track (without recomputing track parameters at each clusters) | |
641 | AliMUONTrack muonTrack; | |
642 | AliMUONESDInterface::ESDToMUON(*esdTrack, muonTrack, kFALSE); | |
643 | ||
644 | // try to match the reconstructed track with a simulated one | |
645 | Int_t nMatchClusters = 0; | |
646 | matchedTrackRef = rc.FindCompatibleTrack(muonTrack, *reconstructibleStore, nMatchClusters, kFALSE, fSigmaCut); | |
647 | if (matchedTrackRef) { | |
648 | ||
649 | containerInput[kVarMatchMC] = static_cast<Double_t>(kTrackerOnly); | |
650 | ||
651 | // simulated track parameters at vertex | |
652 | trackParam = matchedTrackRef->GetTrackParamAtVertex(); | |
653 | x1 = trackParam->GetNonBendingCoor(); | |
654 | y1 = trackParam->GetBendingCoor(); | |
655 | z1 = trackParam->GetZ(); | |
656 | slopex1 = trackParam->GetNonBendingSlope(); | |
657 | slopey1 = trackParam->GetBendingSlope(); | |
658 | pX1 = trackParam->Px(); | |
659 | pY1 = trackParam->Py(); | |
660 | pZ1 = trackParam->Pz(); | |
661 | p1 = trackParam->P(); | |
662 | pT1 = TMath::Sqrt(pX1*pX1 + pY1*pY1); | |
663 | aMC = TMath::ATan(-pT1/pZ1) * TMath::RadToDeg(); | |
664 | eta1 = TMath::Log(TMath::Tan(0.5*TMath::ATan(-pT1/pZ1))); | |
665 | phi1 = TMath::Pi()+TMath::ATan2(-pY1, -pX1); | |
666 | ||
667 | // reconstructed track parameters at the end of the absorber | |
668 | AliMUONTrackParam trackParamAtAbsEnd(*((AliMUONTrackParam*)muonTrack.GetTrackParamAtCluster()->First())); | |
669 | AliMUONTrackExtrap::ExtrapToZ(&trackParamAtAbsEnd, AliMUONConstants::AbsZEnd()); | |
670 | xAbs = trackParamAtAbsEnd.GetNonBendingCoor(); | |
671 | yAbs = trackParamAtAbsEnd.GetBendingCoor(); | |
672 | dAbs = TMath::Sqrt(xAbs*xAbs + yAbs*yAbs); | |
673 | aAbs = TMath::ATan(-dAbs/AliMUONConstants::AbsZEnd()) * TMath::RadToDeg(); | |
674 | pX2 = trackParamAtAbsEnd.Px(); | |
675 | pY2 = trackParamAtAbsEnd.Py(); | |
676 | pZ2 = trackParamAtAbsEnd.Pz(); | |
677 | pT2 = TMath::Sqrt(pX2*pX2 + pY2*pY2); | |
678 | aMCS = TMath::ATan(-pT2/pZ2) * TMath::RadToDeg(); | |
679 | ||
680 | // reconstructed track parameters at vertex | |
681 | trackParam = muonTrack.GetTrackParamAtVertex(); | |
682 | x2 = trackParam->GetNonBendingCoor(); | |
683 | y2 = trackParam->GetBendingCoor(); | |
684 | z2 = trackParam->GetZ(); | |
685 | slopex2 = trackParam->GetNonBendingSlope(); | |
686 | slopey2 = trackParam->GetBendingSlope(); | |
687 | pX2 = trackParam->Px(); | |
688 | pY2 = trackParam->Py(); | |
689 | pZ2 = trackParam->Pz(); | |
690 | p2 = trackParam->P(); | |
691 | pT2 = TMath::Sqrt(pX2*pX2 + pY2*pY2); | |
692 | eta2 = TMath::Log(TMath::Tan(0.5*TMath::ATan(-pT2/pZ2))); | |
693 | phi2 = TMath::Pi()+TMath::ATan2(-pY2, -pX2); | |
694 | ||
695 | // reconstructed track parameters at DCA | |
696 | AliMUONTrackParam trackParamAtDCA(*((AliMUONTrackParam*) muonTrack.GetTrackParamAtCluster()->First())); | |
697 | pU = trackParamAtDCA.P(); | |
698 | AliMUONTrackExtrap::ExtrapToVertexWithoutBranson(&trackParamAtDCA, z2); | |
699 | xDCA = trackParamAtDCA.GetNonBendingCoor(); | |
700 | yDCA = trackParamAtDCA.GetBendingCoor(); | |
701 | dca = TMath::Sqrt(xDCA*xDCA + yDCA*yDCA); | |
702 | ||
703 | dPhi = phi2-phi1; | |
704 | if (dPhi < -TMath::Pi()) dPhi += 2.*TMath::Pi(); | |
705 | else if (dPhi > TMath::Pi()) dPhi -= 2.*TMath::Pi(); | |
706 | ||
707 | // fill histograms | |
708 | static_cast<TH1*>(fTrackerList->At(kResPAtVtx))->Fill(p2-p1); | |
709 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsP))->Fill(p1,p2-p1); | |
710 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsAngleAtAbsEnd))->Fill(aAbs,p2-p1); | |
711 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsMCAngle))->Fill(aMC,p2-p1); | |
712 | static_cast<TH3*>(fTrackerList->At(kResPAtVtxVsAngleAtAbsEndVsP))->Fill(p1,aAbs,p2-p1); | |
713 | static_cast<TH2*>(fTrackerList->At(kResPtAtVtxVsPt))->Fill(pT1,pT2-pT1); | |
714 | ||
715 | static_cast<TH1*>(fTrackerList->At(kResSlopeXAtVtx))->Fill(slopex2-slopex1); | |
716 | static_cast<TH1*>(fTrackerList->At(kResSlopeYAtVtx))->Fill(slopey2-slopey1); | |
717 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsP))->Fill(p1,slopex2-slopex1); | |
718 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsP))->Fill(p1,slopey2-slopey1); | |
719 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsAngleAtAbsEnd))->Fill(aAbs,slopex2-slopex1); | |
720 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsAngleAtAbsEnd))->Fill(aAbs,slopey2-slopey1); | |
721 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsMCAngle))->Fill(aMC,slopex2-slopex1); | |
722 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsMCAngle))->Fill(aMC,slopey2-slopey1); | |
723 | ||
724 | static_cast<TH1*>(fTrackerList->At(kResEtaAtVtx))->Fill(eta2-eta1); | |
725 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsP))->Fill(p1,eta2-eta1); | |
726 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsAngleAtAbsEnd))->Fill(aAbs,eta2-eta1); | |
727 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsMCAngle))->Fill(aMC,eta2-eta1); | |
728 | ||
729 | static_cast<TH1*>(fTrackerList->At(kResPhiAtVtx))->Fill(dPhi); | |
730 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsP))->Fill(p1,dPhi); | |
731 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsAngleAtAbsEnd))->Fill(aAbs,dPhi); | |
732 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsMCAngle))->Fill(aMC,dPhi); | |
733 | ||
734 | static_cast<TH1*>(fTrackerList->At(kPDCA))->Fill(0.5*(p2+pU)*dca); | |
735 | static_cast<TH2*>(fTrackerList->At(kPDCAVsAngleAtAbsEnd))->Fill(aAbs,0.5*(p2+pU)*dca); | |
736 | static_cast<TH2*>(fTrackerList->At(kPDCAVsMCAngle))->Fill(aMC,0.5*(p2+pU)*dca); | |
737 | ||
738 | if (aAbs > 2. && aAbs < 3.) { | |
739 | ||
740 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPIn23deg))->Fill(p1,p2-p1); | |
741 | static_cast<TH2*>(fTrackerList->At(kPDCAVsPIn23deg))->Fill(p1,0.5*(p2+pU)*dca); | |
742 | static_cast<TH2*>(fTrackerList->At(kPMCSAngVsPIn23deg))->Fill(p1,0.5*(p2+pU)*(aMCS-aMC)*TMath::DegToRad()); | |
743 | ||
744 | } else if (aAbs >= 3. && aAbs < 10.) { | |
745 | ||
746 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPIn310deg))->Fill(p1,p2-p1); | |
747 | static_cast<TH2*>(fTrackerList->At(kPDCAVsPIn310deg))->Fill(p1,0.5*(p2+pU)*dca); | |
748 | static_cast<TH2*>(fTrackerList->At(kPMCSAngVsPIn310deg))->Fill(p1,0.5*(p2+pU)*(aMCS-aMC)*TMath::DegToRad()); | |
749 | ||
750 | } | |
751 | ||
752 | if (aMC < 2.) { | |
753 | ||
754 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPIn02degMC))->Fill(p1,p2-p1); | |
755 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPosAbsEndIn02degMC))->Fill(dAbs,p2-p1); | |
756 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsPosAbsEndIn02degMC))->Fill(dAbs,slopex2-slopex1); | |
757 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsPosAbsEndIn02degMC))->Fill(dAbs,slopey2-slopey1); | |
758 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsPosAbsEndIn02degMC))->Fill(dAbs,eta2-eta1); | |
759 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsPosAbsEndIn02degMC))->Fill(dAbs,dPhi); | |
760 | static_cast<TH2*>(fTrackerList->At(kPDCAVsPosAbsEndIn02degMC))->Fill(dAbs,0.5*(p2+pU)*dca); | |
761 | ||
762 | } else if (aMC >= 2. && aMC < 3) { | |
763 | ||
764 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPosAbsEndIn23degMC))->Fill(dAbs,p2-p1); | |
765 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsPosAbsEndIn23degMC))->Fill(dAbs,slopex2-slopex1); | |
766 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsPosAbsEndIn23degMC))->Fill(dAbs,slopey2-slopey1); | |
767 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsPosAbsEndIn23degMC))->Fill(dAbs,eta2-eta1); | |
768 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsPosAbsEndIn23degMC))->Fill(dAbs,dPhi); | |
769 | static_cast<TH2*>(fTrackerList->At(kPDCAVsPosAbsEndIn23degMC))->Fill(dAbs,0.5*(p2+pU)*dca); | |
770 | ||
771 | } else if (aMC >= 3. && aMC < 10.) { | |
772 | ||
773 | static_cast<TH2*>(fTrackerList->At(kResPAtVtxVsPosAbsEndIn310degMC))->Fill(dAbs,p2-p1); | |
774 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAtVtxVsPosAbsEndIn310degMC))->Fill(dAbs,slopex2-slopex1); | |
775 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAtVtxVsPosAbsEndIn310degMC))->Fill(dAbs,slopey2-slopey1); | |
776 | static_cast<TH2*>(fTrackerList->At(kResEtaAtVtxVsPosAbsEndIn310degMC))->Fill(dAbs,eta2-eta1); | |
777 | static_cast<TH2*>(fTrackerList->At(kResPhiAtVtxVsPosAbsEndIn310degMC))->Fill(dAbs,dPhi); | |
778 | static_cast<TH2*>(fTrackerList->At(kPDCAVsPosAbsEndIn310degMC))->Fill(dAbs,0.5*(p2+pU)*dca); | |
779 | ||
780 | } | |
781 | ||
782 | // simulated track parameters at vertex | |
783 | trackParam = (AliMUONTrackParam*) matchedTrackRef->GetTrackParamAtCluster()->First(); | |
784 | x1 = trackParam->GetNonBendingCoor(); | |
785 | y1 = trackParam->GetBendingCoor(); | |
786 | z1 = trackParam->GetZ(); | |
787 | slopex1 = trackParam->GetNonBendingSlope(); | |
788 | slopey1 = trackParam->GetBendingSlope(); | |
789 | pX1 = trackParam->Px(); | |
790 | pY1 = trackParam->Py(); | |
791 | pZ1 = trackParam->Pz(); | |
792 | p1 = trackParam->P(); | |
793 | pT1 = TMath::Sqrt(pX1*pX1 + pY1*pY1); | |
794 | ||
795 | // reconstructed track parameters at vertex | |
796 | trackParam = (AliMUONTrackParam*) muonTrack.GetTrackParamAtCluster()->First(); | |
797 | x2 = trackParam->GetNonBendingCoor(); | |
798 | y2 = trackParam->GetBendingCoor(); | |
799 | z2 = trackParam->GetZ(); | |
800 | slopex2 = trackParam->GetNonBendingSlope(); | |
801 | slopey2 = trackParam->GetBendingSlope(); | |
802 | pX2 = trackParam->Px(); | |
803 | pY2 = trackParam->Py(); | |
804 | pZ2 = trackParam->Pz(); | |
805 | p2 = trackParam->P(); | |
806 | pT2 = TMath::Sqrt(pX2*pX2 + pY2*pY2); | |
807 | ||
808 | // fill histograms | |
809 | static_cast<TH1*>(fTrackerList->At(kResPAt1stCl))->Fill(p2-p1); | |
810 | static_cast<TH2*>(fTrackerList->At(kResPAt1stClVsP))->Fill(p1,p2-p1); | |
811 | static_cast<TH2*>(fTrackerList->At(kResPtAt1stClVsPt))->Fill(pT1,pT2-pT1); | |
812 | static_cast<TH1*>(fTrackerList->At(kResSlopeXAt1stCl))->Fill(slopex2-slopex1); | |
813 | static_cast<TH1*>(fTrackerList->At(kResSlopeYAt1stCl))->Fill(slopey2-slopey1); | |
814 | static_cast<TH2*>(fTrackerList->At(kResSlopeXAt1stClVsP))->Fill(p1,slopex2-slopex1); | |
815 | static_cast<TH2*>(fTrackerList->At(kResSlopeYAt1stClVsP))->Fill(p1,slopey2-slopey1); | |
816 | ||
817 | // clusters residuals | |
818 | for (Int_t iCl1 = 0; iCl1 < muonTrack.GetNClusters(); iCl1++) { | |
819 | ||
820 | AliMUONVCluster* cluster1 = static_cast<AliMUONTrackParam*>(muonTrack.GetTrackParamAtCluster()->UncheckedAt(iCl1))->GetClusterPtr(); | |
821 | Int_t chId = cluster1->GetChamberId(); | |
822 | Int_t deId = cluster1->GetDetElemId(); | |
823 | ||
824 | for (Int_t iCl2 = 0; iCl2 < matchedTrackRef->GetNClusters(); iCl2++) { | |
825 | ||
826 | AliMUONVCluster* cluster2 = static_cast<AliMUONTrackParam*>(matchedTrackRef->GetTrackParamAtCluster()->UncheckedAt(iCl2))->GetClusterPtr(); | |
827 | ||
828 | if (cluster2->GetDetElemId() == deId) { | |
829 | ||
830 | // fill histograms | |
831 | static_cast<TH2*>(fTrackerList->At(kResClXVsCh))->Fill(chId+1, cluster1->GetX()-cluster2->GetX()); | |
832 | static_cast<TH2*>(fTrackerList->At(kResClYVsCh))->Fill(chId+1, cluster1->GetY()-cluster2->GetY()); | |
833 | static_cast<TH2*>(fTrackerList->At(kResClXVsDE))->Fill(fDEIndices[deId], cluster1->GetX()-cluster2->GetX()); | |
834 | static_cast<TH2*>(fTrackerList->At(kResClYVsDE))->Fill(fDEIndices[deId], cluster1->GetY()-cluster2->GetY()); | |
835 | ||
836 | break; | |
837 | ||
838 | } | |
839 | ||
840 | } | |
841 | ||
842 | } | |
843 | ||
844 | } // end if (matchedTrackRef) | |
845 | ||
846 | } // end if (esdTrack->ContainTrackerData()) | |
847 | ||
848 | // Trigger | |
849 | if (esdTrack->ContainTriggerData()) { | |
850 | ||
851 | // Convert ESD track to trigger track | |
852 | AliMUONLocalTrigger locTrg; | |
853 | AliMUONESDInterface::ESDToMUON(*esdTrack, locTrg); | |
854 | AliMUONTriggerTrack trigTrack; | |
855 | rc.TriggerToTrack(locTrg, trigTrack); | |
856 | ||
857 | // try to match the trigger track with the same MC track if any | |
858 | if (matchedTrackRef) { | |
859 | AliMUONTriggerTrack* triggerTrackRef = static_cast<AliMUONTriggerTrack*>(triggerTrackRefStore->FindObject(matchedTrackRef->GetUniqueID())); | |
860 | if (triggerTrackRef && trigTrack.Match(*triggerTrackRef, fSigmaCutTrig)) matchedTrigTrackRef = triggerTrackRef; | |
861 | if (matchedTrigTrackRef) containerInput[kVarMatchMC] = static_cast<Double_t>(kMatchedSame); | |
862 | } | |
863 | ||
864 | // or try to match with any triggerable track | |
865 | if (!matchedTrigTrackRef) { | |
866 | matchedTrigTrackRef = rc.FindCompatibleTrack(trigTrack, *triggerTrackRefStore, fSigmaCutTrig); | |
867 | if (matchedTrigTrackRef) containerInput[kVarMatchMC] = (matchedTrackRef) ? static_cast<Double_t>(kMatchedDiff) : static_cast<Double_t>(kTriggerOnly); | |
868 | } | |
869 | ||
870 | // fill histograms | |
871 | if (matchedTrigTrackRef) { | |
872 | static_cast<TH1*>(fTriggerList->At(kResTrigX11))->Fill(trigTrack.GetX11() - matchedTrigTrackRef->GetX11()); | |
873 | static_cast<TH1*>(fTriggerList->At(kResTrigY11))->Fill(trigTrack.GetY11() - matchedTrigTrackRef->GetY11()); | |
874 | static_cast<TH1*>(fTriggerList->At(kResTrigSlopeY))->Fill(trigTrack.GetSlopeY() - matchedTrigTrackRef->GetSlopeY()); | |
875 | } | |
876 | ||
877 | } | |
878 | ||
879 | // get MC particle ID | |
880 | Int_t mcID = -1; | |
881 | if (matchedTrackRef) mcID = static_cast<Int_t>(matchedTrackRef->GetUniqueID()); | |
882 | else if (matchedTrigTrackRef) mcID = static_cast<Int_t>(matchedTrigTrackRef->GetUniqueID()); | |
883 | ||
884 | // fill particle container | |
885 | FillContainerInfo(containerInput, esdTrack, mcID); | |
886 | fCFContainer->Fill(containerInput, kStepReconstructed); | |
887 | ||
888 | } | |
889 | ||
890 | // ------ Loop over reconstructible tracks ------ | |
891 | AliMUONTrack* trackRef = 0x0; | |
892 | TIter next(reconstructibleStore->CreateIterator()); | |
893 | while ((trackRef = static_cast<AliMUONTrack*>(next()))) { | |
894 | ||
895 | // find the corresponding triggerable track if any | |
896 | AliMUONTriggerTrack* trigTrackRef = static_cast<AliMUONTriggerTrack*>(triggerTrackRefStore->FindObject(trackRef->GetUniqueID())); | |
897 | ||
898 | // fill particle container | |
899 | FillContainerInfo(containerInput, 0x0, static_cast<Int_t>(trackRef->GetUniqueID())); | |
900 | containerInput[kVarHasTracker] = 1.; | |
901 | if (trigTrackRef) containerInput[kVarTrigger] = static_cast<Double_t>(kAllPtTrig); | |
902 | containerInput[kVarMatchMC] = static_cast<Double_t>(kNoMatch); | |
903 | fCFContainer->Fill(containerInput, kStepGeneratedMC); | |
904 | ||
905 | } | |
906 | ||
907 | // ------ Loop over triggerable ghosts ------ | |
908 | AliMUONTriggerTrack* trigTrackRef = 0x0; | |
909 | TIter nextTrig(triggerTrackRefStore->CreateIterator()); | |
910 | while ((trigTrackRef = static_cast<AliMUONTriggerTrack*>(nextTrig()))) { | |
911 | ||
912 | // discard tracks also reconstructible | |
913 | if (reconstructibleStore->FindObject(trigTrackRef->GetUniqueID())) continue; | |
914 | ||
915 | // fill particle container | |
916 | FillContainerInfo(containerInput, 0x0, static_cast<Int_t>(trigTrackRef->GetUniqueID())); | |
917 | containerInput[kVarTrigger] = static_cast<Double_t>(kAllPtTrig); | |
918 | containerInput[kVarMatchMC] = static_cast<Double_t>(kNoMatch); | |
919 | fCFContainer->Fill(containerInput, kStepGeneratedMC); | |
920 | ||
921 | } | |
922 | ||
923 | // Post final data | |
924 | PostData(1, fCFContainer); | |
925 | PostData(3, fTriggerList); | |
926 | PostData(4, fTrackerList); | |
927 | } | |
928 | ||
929 | //________________________________________________________________________ | |
930 | void AliAnalysisTaskMuonPerformance::Terminate(Option_t *) | |
931 | { | |
932 | // | |
933 | /// Draw some histogram at the end. | |
934 | // | |
935 | ||
936 | // do it only locally | |
937 | //if (gROOT->IsBatch()) return; | |
938 | ||
939 | // get output containers | |
940 | fCFContainer = dynamic_cast<AliCFContainer*>(GetOutputData(1)); | |
941 | fTriggerList = dynamic_cast<TObjArray*>(GetOutputData(3)); | |
942 | fTrackerList = dynamic_cast<TObjArray*>(GetOutputData(4)); | |
943 | if (!fCFContainer || !fTriggerList || !fTrackerList) { | |
944 | AliWarning("Output containers not found: summary histograms are not created"); | |
945 | return; | |
946 | } | |
947 | ||
948 | // --- compute efficiencies --- | |
949 | fEfficiencyList = new TObjArray(100); | |
950 | fEfficiencyList->SetOwner(); | |
951 | ||
952 | AliCFEffGrid* efficiency = new AliCFEffGrid("eff","",*fCFContainer); | |
953 | efficiency->CalculateEfficiency(kStepReconstructed, kStepGeneratedMC); | |
954 | Double_t totalEff = 0., totalEffErr = 0.; | |
955 | Int_t sumEffBin = 0; | |
956 | TH1* auxHisto = 0x0; | |
957 | ||
958 | // add histogram summarizing global efficiencies | |
959 | TH1D* effSummary = new TH1D("effSummary", "Efficiency summary", 1, 0., 0.); | |
960 | effSummary->GetYaxis()->SetTitle("Efficiency"); | |
961 | fEfficiencyList->AddLast(effSummary); | |
962 | ||
963 | // Tracker efficiency using all reconstructed tracks | |
964 | efficiency->GetNum()->SetRangeUser(kVarHasTracker, 1., 1.); | |
965 | efficiency->GetDen()->SetRangeUser(kVarHasTracker, 1., 1.); | |
966 | auxHisto = efficiency->Project(kVarPt); | |
967 | auxHisto->SetName("effVsPt_trackerTracks"); | |
968 | fEfficiencyList->AddLast(auxHisto); | |
969 | auxHisto = efficiency->Project(kVarEta); | |
970 | auxHisto->SetName("effVsEta_trackerTracks"); | |
971 | fEfficiencyList->AddLast(auxHisto); | |
972 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
973 | sumEffBin++; | |
974 | effSummary->Fill("Tracker_all", totalEff); | |
975 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
976 | printf("Tracker efficiency using all reconstructed tracks = %f +- %f\n", totalEff, totalEffErr); | |
977 | ||
978 | // Tracker efficiency using tracks matched with reconstructible ones | |
979 | efficiency->GetNum()->SetRangeUser(kVarMatchMC, kTrackerOnly, kMatchedDiff); | |
980 | auxHisto = efficiency->Project(kVarPt); | |
981 | auxHisto->SetName("effVsPt_trackerTracksMatchMC"); | |
982 | fEfficiencyList->AddLast(auxHisto); | |
983 | auxHisto = efficiency->Project(kVarEta); | |
984 | auxHisto->SetName("effVsEta_trackerTracksMatchMC"); | |
985 | fEfficiencyList->AddLast(auxHisto); | |
986 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
987 | sumEffBin++; | |
988 | effSummary->Fill("Tracker_MCId", totalEff); | |
989 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
990 | printf("Tracker efficiency using reconstructed tracks matching MC = %f +- %f\n", totalEff, totalEffErr); | |
991 | ||
992 | // Matched efficiency using all reconstructed tracks | |
993 | efficiency->GetNum()->SetRangeUser(kVarTrigger, kAllPtTrig, kHighPtTrig); | |
994 | efficiency->GetDen()->SetRangeUser(kVarTrigger, kAllPtTrig, kAllPtTrig); | |
995 | efficiency->GetNum()->GetAxis(kVarMatchMC)->SetRange(); | |
996 | auxHisto = efficiency->Project(kVarPt); | |
997 | auxHisto->SetName("effVsPt_matchedTracks"); | |
998 | fEfficiencyList->AddLast(auxHisto); | |
999 | auxHisto = efficiency->Project(kVarEta); | |
1000 | auxHisto->SetName("effVsEta_matchedTracks"); | |
1001 | fEfficiencyList->AddLast(auxHisto); | |
1002 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
1003 | sumEffBin++; | |
1004 | effSummary->Fill("Matched_all", totalEff); | |
1005 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
1006 | printf("Matched efficiency using all reconstructed tracks = %f +- %f\n", totalEff, totalEffErr); | |
1007 | ||
1008 | // Matched efficiency using tracks matched with reconstructible & triggerable ones | |
1009 | efficiency->GetNum()->SetRangeUser(kVarMatchMC, kMatchedSame, kMatchedSame); | |
1010 | auxHisto = efficiency->Project(kVarPt); | |
1011 | auxHisto->SetName("effVsPt_matchedTracksMatchMC"); | |
1012 | fEfficiencyList->AddLast(auxHisto); | |
1013 | auxHisto = efficiency->Project(kVarEta); | |
1014 | auxHisto->SetName("effVsEta_matchedTracksMatchMC"); | |
1015 | fEfficiencyList->AddLast(auxHisto); | |
1016 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
1017 | sumEffBin++; | |
1018 | effSummary->Fill("Matched_MCId", totalEff); | |
1019 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
1020 | printf("Matched efficiency using reconstructed tracks matching MC = %f +- %f\n", totalEff, totalEffErr); | |
1021 | ||
1022 | // Trigger efficiency using all reconstructed tracks | |
1023 | efficiency->GetNum()->GetAxis(kVarHasTracker)->SetRange(); | |
1024 | efficiency->GetDen()->GetAxis(kVarHasTracker)->SetRange(); | |
1025 | efficiency->GetNum()->GetAxis(kVarMatchMC)->SetRange(); | |
1026 | auxHisto = efficiency->Project(kVarPt); | |
1027 | auxHisto->SetName("effVsPt_triggerTracks"); | |
1028 | fEfficiencyList->AddLast(auxHisto); | |
1029 | auxHisto = efficiency->Project(kVarEta); | |
1030 | auxHisto->SetName("effVsEta_triggerTracks"); | |
1031 | fEfficiencyList->AddLast(auxHisto); | |
1032 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
1033 | sumEffBin++; | |
1034 | effSummary->Fill("Trigger_all", totalEff); | |
1035 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
1036 | printf("Trigger efficiency using all reconstructed tracks = %f +- %f\n", totalEff, totalEffErr); | |
1037 | ||
1038 | // Trigger efficiency using tracks matched with triggerable ones | |
1039 | efficiency->GetNum()->SetRangeUser(kVarMatchMC, kMatchedSame, kTriggerOnly); | |
1040 | auxHisto = efficiency->Project(kVarPt); | |
1041 | auxHisto->SetName("effVsPt_triggerTracksMatchMC"); | |
1042 | fEfficiencyList->AddLast(auxHisto); | |
1043 | auxHisto = efficiency->Project(kVarEta); | |
1044 | auxHisto->SetName("effVsEta_triggerTracksMatchMC"); | |
1045 | fEfficiencyList->AddLast(auxHisto); | |
1046 | GetEfficiency(efficiency, totalEff, totalEffErr); | |
1047 | sumEffBin++; | |
1048 | effSummary->Fill("Trigger_MCId", totalEff); | |
1049 | effSummary->SetBinError(sumEffBin, totalEffErr); | |
1050 | printf("Trigger efficiency using reconstructed tracks matching MC = %f +- %f\n", totalEff, totalEffErr); | |
1051 | ||
1052 | // plot histogram summarizing global efficiencies | |
1053 | TCanvas* cEffSummary = new TCanvas("cEffSummary","Efficiency summary",20,20,310,310); | |
1054 | cEffSummary->SetFillColor(10); cEffSummary->SetHighLightColor(10); | |
1055 | cEffSummary->SetLeftMargin(0.15); cEffSummary->SetBottomMargin(0.15); | |
1056 | effSummary->DrawCopy("etext"); | |
1057 | ||
1058 | // --- plot trigger resolution --- | |
1059 | TCanvas* cTriggerResolution = new TCanvas("cTriggerResolution","Trigger resolution",10,10,310,310); | |
1060 | cTriggerResolution->SetFillColor(10); cTriggerResolution->SetHighLightColor(10); | |
1061 | cTriggerResolution->SetLeftMargin(0.15); cTriggerResolution->SetBottomMargin(0.15); | |
1062 | cTriggerResolution->Divide(2,2); | |
1063 | cTriggerResolution->cd(1); | |
1064 | static_cast<TH1*>(fTriggerList->UncheckedAt(kResTrigX11))->DrawCopy(); | |
1065 | cTriggerResolution->cd(2); | |
1066 | static_cast<TH1*>(fTriggerList->UncheckedAt(kResTrigY11))->DrawCopy(); | |
1067 | cTriggerResolution->cd(3); | |
1068 | static_cast<TH1*>(fTriggerList->UncheckedAt(kResTrigSlopeY))->DrawCopy(); | |
1069 | ||
1070 | // --- compute momentum resolution at vertex --- | |
1071 | fPAtVtxList = new TObjArray(100); | |
1072 | fPAtVtxList->SetOwner(); | |
1073 | ||
1074 | // define graphs | |
1075 | TGraphAsymmErrors* gMeanResPAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1076 | gMeanResPAtVtxVsP->SetName("gMeanResPAtVtxVsP"); | |
1077 | gMeanResPAtVtxVsP->SetTitle("<#Delta_{p}> at vertex versus p;p (GeV/c);<#Delta_{p}> (GeV/c)"); | |
1078 | fPAtVtxList->AddAt(gMeanResPAtVtxVsP, kMeanResPAtVtxVsP); | |
1079 | TGraphAsymmErrors* gMostProbResPAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1080 | gMostProbResPAtVtxVsP->SetName("gMostProbResPAtVtxVsP"); | |
1081 | gMostProbResPAtVtxVsP->SetTitle("Most probable #Delta_{p} at vertex versus p;p (GeV/c);Most prob. #Delta_{p} (GeV/c)"); | |
1082 | fPAtVtxList->AddAt(gMostProbResPAtVtxVsP, kMostProbResPAtVtxVsP); | |
1083 | TGraphAsymmErrors* gSigmaResPAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1084 | gSigmaResPAtVtxVsP->SetName("gSigmaResPAtVtxVsP"); | |
1085 | gSigmaResPAtVtxVsP->SetTitle("#sigma_{p}/p at vertex versus p;p (GeV/c);#sigma_{p}/p (%)"); | |
1086 | fPAtVtxList->AddAt(gSigmaResPAtVtxVsP, kSigmaResPAtVtxVsP); | |
1087 | ||
1088 | // fit histo and fill graphs | |
1089 | TH2* h = static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsP)); | |
1090 | FitLandauGausResVsP(h, "momentum residuals at vertex", gMeanResPAtVtxVsP, gMostProbResPAtVtxVsP, gSigmaResPAtVtxVsP); | |
1091 | ||
1092 | // convert resolution into relative resolution | |
1093 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/fNPBins, 1); | |
1094 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1095 | Double_t x,y; | |
1096 | gSigmaResPAtVtxVsP->GetPoint(i/rebinFactorX-1, x, y); | |
1097 | gSigmaResPAtVtxVsP->SetPoint(i/rebinFactorX-1, x, 100.*y/x); | |
1098 | gSigmaResPAtVtxVsP->SetPointEYlow(i/rebinFactorX-1, 100.*gSigmaResPAtVtxVsP->GetErrorYlow(i/rebinFactorX-1)/x); | |
1099 | gSigmaResPAtVtxVsP->SetPointEYhigh(i/rebinFactorX-1, 100.*gSigmaResPAtVtxVsP->GetErrorYhigh(i/rebinFactorX-1)/x); | |
1100 | } | |
1101 | ||
1102 | // --- compute momentum resolution at first cluster --- | |
1103 | fPAt1stClList = new TObjArray(100); | |
1104 | fPAt1stClList->SetOwner(); | |
1105 | ||
1106 | // define graphs | |
1107 | TGraphAsymmErrors* gMeanResPAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1108 | gMeanResPAt1stClVsP->SetName("gMeanResPAt1stClVsP"); | |
1109 | gMeanResPAt1stClVsP->SetTitle("<#Delta_{p}> at first cluster versus p;p (GeV/c);<#Delta_{p}> (GeV/c)"); | |
1110 | fPAt1stClList->AddAt(gMeanResPAt1stClVsP, kMeanResPAt1stClVsP); | |
1111 | TGraphAsymmErrors* gSigmaResPAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1112 | gSigmaResPAt1stClVsP->SetName("gSigmaResPAt1stClVsP"); | |
1113 | gSigmaResPAt1stClVsP->SetTitle("#sigma_{p}/p at first cluster versus p;p (GeV/c);#sigma_{p}/p (%)"); | |
1114 | fPAt1stClList->AddAt(gSigmaResPAt1stClVsP, kSigmaResPAt1stClVsP); | |
1115 | ||
1116 | // fit histo and fill graphs | |
1117 | h = static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAt1stClVsP)); | |
1118 | FitGausResVsMom(h, 0., 1., "momentum residuals at first cluster", gMeanResPAt1stClVsP, gSigmaResPAt1stClVsP); | |
1119 | ||
1120 | // convert resolution into relative resolution | |
1121 | rebinFactorX = TMath::Max(h->GetNbinsX()/fNPBins, 1); | |
1122 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1123 | Double_t x,y; | |
1124 | gSigmaResPAt1stClVsP->GetPoint(i/rebinFactorX-1, x, y); | |
1125 | gSigmaResPAt1stClVsP->SetPoint(i/rebinFactorX-1, x, 100.*y/x); | |
1126 | gSigmaResPAt1stClVsP->SetPointEYlow(i/rebinFactorX-1, 100.*gSigmaResPAt1stClVsP->GetErrorYlow(i/rebinFactorX-1)/x); | |
1127 | gSigmaResPAt1stClVsP->SetPointEYhigh(i/rebinFactorX-1, 100.*gSigmaResPAt1stClVsP->GetErrorYhigh(i/rebinFactorX-1)/x); | |
1128 | } | |
1129 | ||
1130 | // --- compute slope resolution at vertex --- | |
1131 | fSlopeAtVtxList = new TObjArray(100); | |
1132 | fSlopeAtVtxList->SetOwner(); | |
1133 | ||
1134 | // define graphs | |
1135 | TGraphAsymmErrors* gMeanResSlopeXAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1136 | gMeanResSlopeXAtVtxVsP->SetName("gMeanResSlopeXAtVtxVsP"); | |
1137 | gMeanResSlopeXAtVtxVsP->SetTitle("<#Delta_{slope_{X}}> at vertex versus p;p (GeV/c);<#Delta_{slope_{X}}>"); | |
1138 | fSlopeAtVtxList->AddAt(gMeanResSlopeXAtVtxVsP, kMeanResSlopeXAtVtxVsP); | |
1139 | TGraphAsymmErrors* gMeanResSlopeYAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1140 | gMeanResSlopeYAtVtxVsP->SetName("gMeanResSlopeYAtVtxVsP"); | |
1141 | gMeanResSlopeYAtVtxVsP->SetTitle("<#Delta_{slope_{Y}}> at vertex versus p;p (GeV/c);<#Delta_{slope_{Y}}>"); | |
1142 | fSlopeAtVtxList->AddAt(gMeanResSlopeYAtVtxVsP, kMeanResSlopeYAtVtxVsP); | |
1143 | TGraphAsymmErrors* gSigmaResSlopeXAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1144 | gSigmaResSlopeXAtVtxVsP->SetName("gSigmaResSlopeXAtVtxVsP"); | |
1145 | gSigmaResSlopeXAtVtxVsP->SetTitle("#sigma_{slope_{X}} at vertex versus p;p (GeV/c);#sigma_{slope_{X}}"); | |
1146 | fSlopeAtVtxList->AddAt(gSigmaResSlopeXAtVtxVsP, kSigmaResSlopeXAtVtxVsP); | |
1147 | TGraphAsymmErrors* gSigmaResSlopeYAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1148 | gSigmaResSlopeYAtVtxVsP->SetName("gSigmaResSlopeYAtVtxVsP"); | |
1149 | gSigmaResSlopeYAtVtxVsP->SetTitle("#sigma_{slope_{Y}} at vertex versus p;p (GeV/c);#sigma_{slope_{Y}}"); | |
1150 | fSlopeAtVtxList->AddAt(gSigmaResSlopeYAtVtxVsP, kSigmaResSlopeYAtVtxVsP); | |
1151 | ||
1152 | // fit histo and fill graphs | |
1153 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsP)), 0., 2.e-3, | |
1154 | "slopeX residuals at vertex", gMeanResSlopeXAtVtxVsP, gSigmaResSlopeXAtVtxVsP); | |
1155 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsP)), 0., 2.e-3, | |
1156 | "slopeY residuals at vertex", gMeanResSlopeYAtVtxVsP, gSigmaResSlopeYAtVtxVsP); | |
1157 | ||
1158 | // --- compute slope resolution at first cluster --- | |
1159 | fSlopeAt1stClList = new TObjArray(100); | |
1160 | fSlopeAt1stClList->SetOwner(); | |
1161 | ||
1162 | // define graphs | |
1163 | TGraphAsymmErrors* gMeanResSlopeXAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1164 | gMeanResSlopeXAt1stClVsP->SetName("gMeanResSlopeXAt1stClVsP"); | |
1165 | gMeanResSlopeXAt1stClVsP->SetTitle("<#Delta_{slope_{X}}> at first cluster versus p;p (GeV/c);<#Delta_{slope_{X}}>"); | |
1166 | fSlopeAt1stClList->AddAt(gMeanResSlopeXAt1stClVsP, kMeanResSlopeXAt1stClVsP); | |
1167 | TGraphAsymmErrors* gMeanResSlopeYAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1168 | gMeanResSlopeYAt1stClVsP->SetName("gMeanResSlopeYAt1stClVsP"); | |
1169 | gMeanResSlopeYAt1stClVsP->SetTitle("<#Delta_{slope_{Y}}> at first cluster versus p;p (GeV/c);<#Delta_{slope_{Y}}>"); | |
1170 | fSlopeAt1stClList->AddAt(gMeanResSlopeYAt1stClVsP, kMeanResSlopeYAt1stClVsP); | |
1171 | TGraphAsymmErrors* gSigmaResSlopeXAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1172 | gSigmaResSlopeXAt1stClVsP->SetName("gSigmaResSlopeXAt1stClVsP"); | |
1173 | gSigmaResSlopeXAt1stClVsP->SetTitle("#sigma_{slope_{X}} at first cluster versus p;p (GeV/c);#sigma_{slope_{X}}"); | |
1174 | fSlopeAt1stClList->AddAt(gSigmaResSlopeXAt1stClVsP, kSigmaResSlopeXAt1stClVsP); | |
1175 | TGraphAsymmErrors* gSigmaResSlopeYAt1stClVsP = new TGraphAsymmErrors(fNPBins); | |
1176 | gSigmaResSlopeYAt1stClVsP->SetName("gSigmaResSlopeYAt1stClVsP"); | |
1177 | gSigmaResSlopeYAt1stClVsP->SetTitle("#sigma_{slope_{Y}} at first cluster versus p;p (GeV/c);#sigma_{slope_{Y}}"); | |
1178 | fSlopeAt1stClList->AddAt(gSigmaResSlopeYAt1stClVsP, kSigmaResSlopeYAt1stClVsP); | |
1179 | ||
1180 | // fit histo and fill graphs | |
1181 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAt1stClVsP)), 0., 3.e-4, | |
1182 | "slopeX residuals at first cluster", gMeanResSlopeXAt1stClVsP, gSigmaResSlopeXAt1stClVsP); | |
1183 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAt1stClVsP)), 0., 3.e-4, | |
1184 | "slopeY residuals at first cluster", gMeanResSlopeYAt1stClVsP, gSigmaResSlopeYAt1stClVsP); | |
1185 | ||
1186 | // --- compute eta resolution at vertex --- | |
1187 | fEtaAtVtxList = new TObjArray(100); | |
1188 | fEtaAtVtxList->SetOwner(); | |
1189 | ||
1190 | // define graphs | |
1191 | TGraphAsymmErrors* gMeanResEtaAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1192 | gMeanResEtaAtVtxVsP->SetName("gMeanResEtaAtVtxVsP"); | |
1193 | gMeanResEtaAtVtxVsP->SetTitle("<#Delta_{eta}> at vertex versus p;p (GeV/c);<#Delta_{eta}>"); | |
1194 | fEtaAtVtxList->AddAt(gMeanResEtaAtVtxVsP, kMeanResEtaAtVtxVsP); | |
1195 | TGraphAsymmErrors* gSigmaResEtaAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1196 | gSigmaResEtaAtVtxVsP->SetName("gSigmaResEtaAtVtxVsP"); | |
1197 | gSigmaResEtaAtVtxVsP->SetTitle("#sigma_{eta} at vertex versus p;p (GeV/c);#sigma_{eta}"); | |
1198 | fEtaAtVtxList->AddAt(gSigmaResEtaAtVtxVsP, kSigmaResEtaAtVtxVsP); | |
1199 | ||
1200 | // fit histo and fill graphs | |
1201 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsP)), 0., 0.1, | |
1202 | "eta residuals at vertex", gMeanResEtaAtVtxVsP, gSigmaResEtaAtVtxVsP); | |
1203 | ||
1204 | // --- compute phi resolution at vertex --- | |
1205 | fPhiAtVtxList = new TObjArray(100); | |
1206 | fPhiAtVtxList->SetOwner(); | |
1207 | ||
1208 | // define graphs | |
1209 | TGraphAsymmErrors* gMeanResPhiAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1210 | gMeanResPhiAtVtxVsP->SetName("gMeanResPhiAtVtxVsP"); | |
1211 | gMeanResPhiAtVtxVsP->SetTitle("<#Delta_{phi}> at vertex versus p;p (GeV/c);<#Delta_{phi}>"); | |
1212 | fPhiAtVtxList->AddAt(gMeanResPhiAtVtxVsP, kMeanResPhiAtVtxVsP); | |
1213 | TGraphAsymmErrors* gSigmaResPhiAtVtxVsP = new TGraphAsymmErrors(fNPBins); | |
1214 | gSigmaResPhiAtVtxVsP->SetName("gSigmaResPhiAtVtxVsP"); | |
1215 | gSigmaResPhiAtVtxVsP->SetTitle("#sigma_{phi} at vertex versus p;p (GeV/c);#sigma_{phi}"); | |
1216 | fPhiAtVtxList->AddAt(gSigmaResPhiAtVtxVsP, kSigmaResPhiAtVtxVsP); | |
1217 | ||
1218 | // fit histo and fill graphs | |
1219 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsP)), 0., 0.01, | |
1220 | "phi residuals at vertex", gMeanResPhiAtVtxVsP, gSigmaResPhiAtVtxVsP); | |
1221 | ||
1222 | // --- compute DCA resolution and MCS dispersion --- | |
1223 | fDCAList = new TObjArray(100); | |
1224 | fDCAList->SetOwner(); | |
1225 | ||
1226 | // define graphs | |
1227 | TGraphAsymmErrors* gMeanPDCAVsPIn23deg = new TGraphAsymmErrors(fNPBins); | |
1228 | gMeanPDCAVsPIn23deg->SetName("gMeanPDCAVsPIn23deg"); | |
1229 | gMeanPDCAVsPIn23deg->SetTitle("<p #times DCA> versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);<p #times DCA> (GeV #times cm)"); | |
1230 | fDCAList->AddAt(gMeanPDCAVsPIn23deg, kMeanPDCAVsPIn23deg); | |
1231 | TGraphAsymmErrors* gSigmaPDCAVsPIn23deg = new TGraphAsymmErrors(fNPBins); | |
1232 | gSigmaPDCAVsPIn23deg->SetName("gSigmaPDCAVsPIn23deg"); | |
1233 | gSigmaPDCAVsPIn23deg->SetTitle("#sigma_{p #times DCA} versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);#sigma_{p #times DCA} (GeV #times cm)"); | |
1234 | fDCAList->AddAt(gSigmaPDCAVsPIn23deg, kSigmaPDCAVsPIn23deg); | |
1235 | TGraphAsymmErrors* gMeanPDCAVsPIn310deg = new TGraphAsymmErrors(fNPBins); | |
1236 | gMeanPDCAVsPIn310deg->SetName("gMeanPDCAVsPIn310deg"); | |
1237 | gMeanPDCAVsPIn310deg->SetTitle("<p #times DCA> versus p for tracks within [3,10[ degrees at absorber end;p (GeV/c);<p #times DCA> (GeV #times cm)"); | |
1238 | fDCAList->AddAt(gMeanPDCAVsPIn310deg, kMeanPDCAVsPIn310deg); | |
1239 | TGraphAsymmErrors* gSigmaPDCAVsPIn310deg = new TGraphAsymmErrors(fNPBins); | |
1240 | gSigmaPDCAVsPIn310deg->SetName("gSigmaPDCAVsPIn310deg"); | |
1241 | gSigmaPDCAVsPIn310deg->SetTitle("#sigma_{p #times DCA} versus p for tracks within [3,10[ degrees at absorber end;p (GeV/c);#sigma_{p #times DCA} (GeV #times cm)"); | |
1242 | fDCAList->AddAt(gSigmaPDCAVsPIn310deg, kSigmaPDCAVsPIn310deg); | |
1243 | ||
1244 | TGraphAsymmErrors* gMeanPMCSAngVsPIn23deg = new TGraphAsymmErrors(fNPBins); | |
1245 | gMeanPMCSAngVsPIn23deg->SetName("gMeanPMCSAngVsPIn23deg"); | |
1246 | gMeanPMCSAngVsPIn23deg->SetTitle("<p #times #Delta#theta_{MCS}> versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);<p #times #Delta#theta_{MCS}> (GeV)"); | |
1247 | fDCAList->AddAt(gMeanPMCSAngVsPIn23deg, kMeanPMCSAngVsPIn23deg); | |
1248 | TGraphAsymmErrors* gSigmaPMCSAngVsPIn23deg = new TGraphAsymmErrors(fNPBins); | |
1249 | gSigmaPMCSAngVsPIn23deg->SetName("gSigmaPMCSAngVsPIn23deg"); | |
1250 | gSigmaPMCSAngVsPIn23deg->SetTitle("#sigma_{p #times #Delta#theta_{MCS}} versus p for tracks within [2,3[ degrees at absorber end;p (GeV/c);#sigma_{p #times #Delta#theta_{MCS}} (GeV)"); | |
1251 | fDCAList->AddAt(gSigmaPMCSAngVsPIn23deg, kSigmaPMCSAngVsPIn23deg); | |
1252 | TGraphAsymmErrors* gMeanPMCSAngVsPIn310deg = new TGraphAsymmErrors(fNPBins); | |
1253 | gMeanPMCSAngVsPIn310deg->SetName("gMeanPMCSAngVsPIn310deg"); | |
1254 | gMeanPMCSAngVsPIn310deg->SetTitle("<p #times #Delta#theta_{MCS}> versus p for tracks within [3,10[ degrees at absorber end;p (GeV/c);<p #times #Delta#theta_{MCS}> (GeV)"); | |
1255 | fDCAList->AddAt(gMeanPMCSAngVsPIn310deg, kMeanPMCSAngVsPIn310deg); | |
1256 | TGraphAsymmErrors* gSigmaPMCSAngVsPIn310deg = new TGraphAsymmErrors(fNPBins); | |
1257 | gSigmaPMCSAngVsPIn310deg->SetName("gSigmaPMCSAngVsPIn310deg"); | |
1258 | gSigmaPMCSAngVsPIn310deg->SetTitle("#sigma_{p #times #Delta#theta_{MCS}} versus p for tracks within [3,10[ degrees at absorber end;p (GeV/c);#sigma_{p #times #Delta#theta_{MCS}} (GeV)"); | |
1259 | fDCAList->AddAt(gSigmaPMCSAngVsPIn310deg, kSigmaPMCSAngVsPIn310deg); | |
1260 | ||
1261 | // fit histo and fill graphs | |
1262 | FitPDCAVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsPIn23deg)), | |
1263 | "p*DCA (tracks in [2,3] deg.)", gMeanPDCAVsPIn23deg, gSigmaPDCAVsPIn23deg); | |
1264 | FitPDCAVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsPIn310deg)), | |
1265 | "p*DCA (tracks in [3,10] deg.)", gMeanPDCAVsPIn310deg, gSigmaPDCAVsPIn310deg); | |
1266 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kPMCSAngVsPIn23deg)), 0., 2.e-3, | |
1267 | "p*MCSAngle (tracks in [2,3] deg.)", gMeanPMCSAngVsPIn23deg, gSigmaPMCSAngVsPIn23deg); | |
1268 | FitGausResVsMom(static_cast<TH2*>(fTrackerList->UncheckedAt(kPMCSAngVsPIn310deg)), 0., 2.e-3, | |
1269 | "p*MCSAngle (tracks in [3,10] deg.)", gMeanPMCSAngVsPIn310deg, gSigmaPMCSAngVsPIn310deg); | |
1270 | ||
1271 | // --- compute cluster resolution --- | |
1272 | fClusterList = new TObjArray(100); | |
1273 | fClusterList->SetOwner(); | |
1274 | ||
1275 | // define graphs per chamber | |
1276 | TGraphErrors* gMeanResClXVsCh = new TGraphErrors(AliMUONConstants::NTrackingCh()); | |
1277 | gMeanResClXVsCh->SetName("gMeanResClXVsCh"); | |
1278 | gMeanResClXVsCh->SetTitle("cluster-trackRef residual-X per Ch: mean;chamber ID;<#Delta_{X}> (cm)"); | |
1279 | gMeanResClXVsCh->SetMarkerStyle(kFullDotLarge); | |
1280 | fClusterList->AddAt(gMeanResClXVsCh, kMeanResClXVsCh); | |
1281 | TGraphErrors* gMeanResClYVsCh = new TGraphErrors(AliMUONConstants::NTrackingCh()); | |
1282 | gMeanResClYVsCh->SetName("gMeanResClYVsCh"); | |
1283 | gMeanResClYVsCh->SetTitle("cluster-trackRef residual-Y per Ch: mean;chamber ID;<#Delta_{Y}> (cm)"); | |
1284 | gMeanResClYVsCh->SetMarkerStyle(kFullDotLarge); | |
1285 | fClusterList->AddAt(gMeanResClYVsCh, kMeanResClYVsCh); | |
1286 | TGraphErrors* gSigmaResClXVsCh = new TGraphErrors(AliMUONConstants::NTrackingCh()); | |
1287 | gSigmaResClXVsCh->SetName("gSigmaResClXVsCh"); | |
1288 | gSigmaResClXVsCh->SetTitle("cluster-trackRef residual-X per Ch: sigma;chamber ID;#sigma_{X} (cm)"); | |
1289 | gSigmaResClXVsCh->SetMarkerStyle(kFullDotLarge); | |
1290 | fClusterList->AddAt(gSigmaResClXVsCh, kSigmaResClXVsCh); | |
1291 | TGraphErrors* gSigmaResClYVsCh = new TGraphErrors(AliMUONConstants::NTrackingCh()); | |
1292 | gSigmaResClYVsCh->SetName("gSigmaResClYVsCh"); | |
1293 | gSigmaResClYVsCh->SetTitle("cluster-trackRef residual-Y per Ch: sigma;chamber ID;#sigma_{Y} (cm)"); | |
1294 | gSigmaResClYVsCh->SetMarkerStyle(kFullDotLarge); | |
1295 | fClusterList->AddAt(gSigmaResClYVsCh, kSigmaResClYVsCh); | |
1296 | ||
1297 | // define graphs per DE | |
1298 | TGraphErrors* gMeanResClXVsDE = new TGraphErrors(fNDE); | |
1299 | gMeanResClXVsDE->SetName("gMeanResClXVsDE"); | |
1300 | gMeanResClXVsDE->SetTitle("cluster-trackRef residual-X per DE: mean;DE ID;<#Delta_{X}> (cm)"); | |
1301 | gMeanResClXVsDE->SetMarkerStyle(kFullDotLarge); | |
1302 | fClusterList->AddAt(gMeanResClXVsDE, kMeanResClXVsDE); | |
1303 | TGraphErrors* gMeanResClYVsDE = new TGraphErrors(fNDE); | |
1304 | gMeanResClYVsDE->SetName("gMeanResClYVsDE"); | |
1305 | gMeanResClYVsDE->SetTitle("cluster-trackRef residual-Y per dE: mean;DE ID;<#Delta_{Y}> (cm)"); | |
1306 | gMeanResClYVsDE->SetMarkerStyle(kFullDotLarge); | |
1307 | fClusterList->AddAt(gMeanResClYVsDE, kMeanResClYVsDE); | |
1308 | TGraphErrors* gSigmaResClXVsDE = new TGraphErrors(fNDE); | |
1309 | gSigmaResClXVsDE->SetName("gSigmaResClXVsDE"); | |
1310 | gSigmaResClXVsDE->SetTitle("cluster-trackRef residual-X per DE: sigma;DE ID;#sigma_{X} (cm)"); | |
1311 | gSigmaResClXVsDE->SetMarkerStyle(kFullDotLarge); | |
1312 | fClusterList->AddAt(gSigmaResClXVsDE, kSigmaResClXVsDE); | |
1313 | TGraphErrors* gSigmaResClYVsDE = new TGraphErrors(fNDE); | |
1314 | gSigmaResClYVsDE->SetName("gSigmaResClYVsDE"); | |
1315 | gSigmaResClYVsDE->SetTitle("cluster-trackRef residual-Y per DE: sigma;DE ID;#sigma_{Y} (cm)"); | |
1316 | gSigmaResClYVsDE->SetMarkerStyle(kFullDotLarge); | |
1317 | fClusterList->AddAt(gSigmaResClYVsDE, kSigmaResClYVsDE); | |
1318 | ||
1319 | // fit histo and fill graphs per chamber | |
1320 | Double_t clusterResPerCh[10][2]; | |
1321 | for (Int_t i = 0; i < AliMUONConstants::NTrackingCh(); i++) { | |
1322 | TH1D *tmp = static_cast<TH2*>(fTrackerList->UncheckedAt(kResClXVsCh))->ProjectionY("tmp",i+1,i+1,"e"); | |
1323 | FitClusterResidual(tmp, i, clusterResPerCh[i][0], gMeanResClXVsCh, gSigmaResClXVsCh); | |
1324 | delete tmp; | |
1325 | tmp = static_cast<TH2*>(fTrackerList->UncheckedAt(kResClYVsCh))->ProjectionY("tmp",i+1,i+1,"e"); | |
1326 | FitClusterResidual(tmp, i, clusterResPerCh[i][1], gMeanResClYVsCh, gSigmaResClYVsCh); | |
1327 | delete tmp; | |
1328 | } | |
1329 | ||
1330 | // fit histo and fill graphs per DE | |
1331 | Double_t clusterResPerDE[200][2]; | |
1332 | for (Int_t i = 0; i < fNDE; i++) { | |
1333 | TH1D *tmp = static_cast<TH2*>(fTrackerList->UncheckedAt(kResClXVsDE))->ProjectionY("tmp",i+1,i+1,"e"); | |
1334 | FitClusterResidual(tmp, i, clusterResPerDE[i][0], gMeanResClXVsDE, gSigmaResClXVsDE); | |
1335 | delete tmp; | |
1336 | tmp = static_cast<TH2*>(fTrackerList->UncheckedAt(kResClYVsDE))->ProjectionY("tmp",i+1,i+1,"e"); | |
1337 | FitClusterResidual(tmp, i, clusterResPerDE[i][1], gMeanResClYVsDE, gSigmaResClYVsDE); | |
1338 | delete tmp; | |
1339 | } | |
1340 | ||
1341 | // set DE graph labels | |
1342 | TAxis* xAxis = static_cast<TH2*>(fTrackerList->UncheckedAt(kResClXVsDE))->GetXaxis(); | |
1343 | gMeanResClXVsDE->GetXaxis()->Set(fNDE, 0.5, fNDE+0.5); | |
1344 | gMeanResClYVsDE->GetXaxis()->Set(fNDE, 0.5, fNDE+0.5); | |
1345 | gSigmaResClXVsDE->GetXaxis()->Set(fNDE, 0.5, fNDE+0.5); | |
1346 | gSigmaResClYVsDE->GetXaxis()->Set(fNDE, 0.5, fNDE+0.5); | |
1347 | for (Int_t i = 1; i <= fNDE; i++) { | |
1348 | const char* label = xAxis->GetBinLabel(i); | |
1349 | gMeanResClXVsDE->GetXaxis()->SetBinLabel(i, label); | |
1350 | gMeanResClYVsDE->GetXaxis()->SetBinLabel(i, label); | |
1351 | gSigmaResClXVsDE->GetXaxis()->SetBinLabel(i, label); | |
1352 | gSigmaResClYVsDE->GetXaxis()->SetBinLabel(i, label); | |
1353 | } | |
1354 | ||
1355 | // --- diplay momentum residuals at vertex --- | |
1356 | TCanvas* cResPAtVtx = DrawVsAng("cResPAtVtx", "momentum residual at vertex in 3 angular regions", | |
1357 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResPAtVtx)), | |
1358 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsAngleAtAbsEnd))); | |
1359 | fPAtVtxList->AddAt(cResPAtVtx, kcResPAtVtx); | |
1360 | TCanvas* cResPAtVtxMC = DrawVsAng("cResPAtVtxMC", "momentum residual at vertex in 3 MC angular regions", | |
1361 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResPAtVtx)), | |
1362 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsMCAngle))); | |
1363 | fPAtVtxList->AddAt(cResPAtVtxMC, kcResPAtVtxMC); | |
1364 | TCanvas* cResPAtVtxVsPosAbsEndMC = DrawVsPos("cResPAtVtxVsPosAbsEndMC", "momentum residual at vertex versus position at absorber end in 3 MC angular regions", | |
1365 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPosAbsEndIn02degMC)), | |
1366 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPosAbsEndIn23degMC)), | |
1367 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPosAbsEndIn310degMC))); | |
1368 | fPAtVtxList->AddAt(cResPAtVtxVsPosAbsEndMC, kcResPAtVtxVsPosAbsEndMC); | |
1369 | TCanvas* cResPAtVtxVsPIn23deg = DrawFitLandauGausResPVsP("cResPAtVtxVsPIn23deg", "momentum residual for tracks between 2 and 3 degrees", | |
1370 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPIn23deg)), | |
1371 | 10, "momentum residuals at vertex (tracks in [2,3] deg.)"); | |
1372 | fPAtVtxList->AddAt(cResPAtVtxVsPIn23deg, kcResPAtVtxVsPIn23deg); | |
1373 | TCanvas* cResPAtVtxVsPIn310deg = DrawFitLandauGausResPVsP("cResPAtVtxVsPIn310deg", "momentum residual for tracks between 3 and 10 degrees", | |
1374 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPIn310deg)), | |
1375 | 10, "momentum residuals at vertex (tracks in [3,10] deg.)"); | |
1376 | fPAtVtxList->AddAt(cResPAtVtxVsPIn310deg, kcResPAtVtxVsPIn310deg); | |
1377 | TCanvas* cResPAtVtxVsPIn02degMC = DrawResPVsP("cResPAtVtxVsPIn02degMC", "momentum residuals for tracks with MC angle < 2 degrees", | |
1378 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPAtVtxVsPIn02degMC)), 5); | |
1379 | fPAtVtxList->AddAt(cResPAtVtxVsPIn02degMC, kcResPAtVtxVsPIn02degMC); | |
1380 | ||
1381 | // --- diplay slopeX residuals at vertex --- | |
1382 | TCanvas* cResSlopeXAtVtx = DrawVsAng("cResSlopeXAtVtx", "slope_{X} residual at vertex in 3 angular regions", | |
1383 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResSlopeXAtVtx)), | |
1384 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsAngleAtAbsEnd))); | |
1385 | fSlopeAtVtxList->AddAt(cResSlopeXAtVtx, kcResSlopeXAtVtx); | |
1386 | TCanvas* cResSlopeYAtVtx = DrawVsAng("cResSlopeYAtVtx", "slope_{Y} residual at vertex in 3 angular regions", | |
1387 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResSlopeYAtVtx)), | |
1388 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsAngleAtAbsEnd))); | |
1389 | fSlopeAtVtxList->AddAt(cResSlopeYAtVtx, kcResSlopeYAtVtx); | |
1390 | TCanvas* cResSlopeXAtVtxMC = DrawVsAng("cResSlopeXAtVtxMC", "slope_{X} residual at vertex in 3 MC angular regions", | |
1391 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResSlopeXAtVtx)), | |
1392 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsMCAngle))); | |
1393 | fSlopeAtVtxList->AddAt(cResSlopeXAtVtxMC, kcResSlopeXAtVtxMC); | |
1394 | TCanvas* cResSlopeYAtVtxMC = DrawVsAng("cResSlopeYAtVtxMC", "slope_{Y} residual at vertex in 3 MC angular regions", | |
1395 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResSlopeYAtVtx)), | |
1396 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsMCAngle))); | |
1397 | fSlopeAtVtxList->AddAt(cResSlopeYAtVtxMC, kcResSlopeYAtVtxMC); | |
1398 | TCanvas* cResSlopeXAtVtxVsPosAbsEndMC = DrawVsPos("cResSlopeXAtVtxVsPosAbsEndMC", "slope_{X} residual at vertex versus position at absorber end in 3 MC angular regions", | |
1399 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsPosAbsEndIn02degMC)), | |
1400 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsPosAbsEndIn23degMC)), | |
1401 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeXAtVtxVsPosAbsEndIn310degMC))); | |
1402 | fSlopeAtVtxList->AddAt(cResSlopeXAtVtxVsPosAbsEndMC, kcResSlopeXAtVtxVsPosAbsEndMC); | |
1403 | TCanvas* cResSlopeYAtVtxVsPosAbsEndMC = DrawVsPos("cResSlopeYAtVtxVsPosAbsEndMC", "slope_{Y} residual at vertex versus position at absorber end in 3 MC angular regions", | |
1404 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsPosAbsEndIn02degMC)), | |
1405 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsPosAbsEndIn23degMC)), | |
1406 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResSlopeYAtVtxVsPosAbsEndIn310degMC))); | |
1407 | fSlopeAtVtxList->AddAt(cResSlopeYAtVtxVsPosAbsEndMC, kcResSlopeYAtVtxVsPosAbsEndMC); | |
1408 | ||
1409 | // --- diplay eta residuals at vertex --- | |
1410 | TCanvas* cResEtaAtVtx = DrawVsAng("cResEtaAtVtx", "eta residual at vertex in 3 angular regions", | |
1411 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResEtaAtVtx)), | |
1412 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsAngleAtAbsEnd))); | |
1413 | fEtaAtVtxList->AddAt(cResEtaAtVtx, kcResEtaAtVtx); | |
1414 | TCanvas* cResEtaAtVtxMC = DrawVsAng("cResEtaAtVtxMC", "eta residual at vertex in 3 MC angular regions", | |
1415 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResEtaAtVtx)), | |
1416 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsMCAngle))); | |
1417 | fEtaAtVtxList->AddAt(cResEtaAtVtxMC, kcResEtaAtVtxMC); | |
1418 | TCanvas* cResEtaAtVtxVsPosAbsEndMC = DrawVsPos("cResEtaAtVtxVsPosAbsEndMC", "eta residual at vertex versus position at absorber end in 3 MC angular regions", | |
1419 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsPosAbsEndIn02degMC)), | |
1420 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsPosAbsEndIn23degMC)), | |
1421 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResEtaAtVtxVsPosAbsEndIn310degMC))); | |
1422 | fEtaAtVtxList->AddAt(cResEtaAtVtxVsPosAbsEndMC, kcResEtaAtVtxVsPosAbsEndMC); | |
1423 | ||
1424 | // --- diplay phi residuals at vertex --- | |
1425 | TCanvas* cResPhiAtVtx = DrawVsAng("cResPhiAtVtx", "phi residual at vertex in 3 angular regions", | |
1426 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResPhiAtVtx)), | |
1427 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsAngleAtAbsEnd))); | |
1428 | fPhiAtVtxList->AddAt(cResPhiAtVtx, kcResPhiAtVtx); | |
1429 | TCanvas* cResPhiAtVtxMC = DrawVsAng("cResPhiAtVtxMC", "phi residual at vertex in 3 MC angular regions", | |
1430 | static_cast<TH1*>(fTrackerList->UncheckedAt(kResPhiAtVtx)), | |
1431 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsMCAngle))); | |
1432 | fPhiAtVtxList->AddAt(cResPhiAtVtxMC, kcResPhiAtVtxMC); | |
1433 | TCanvas* cResPhiAtVtxVsPosAbsEndMC = DrawVsPos("cResPhiAtVtxVsPosAbsEndMC", "phi residual at vertex versus position at absorber end in 3 MC angular regions", | |
1434 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsPosAbsEndIn02degMC)), | |
1435 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsPosAbsEndIn23degMC)), | |
1436 | static_cast<TH2*>(fTrackerList->UncheckedAt(kResPhiAtVtxVsPosAbsEndIn310degMC))); | |
1437 | fPhiAtVtxList->AddAt(cResPhiAtVtxVsPosAbsEndMC, kcResPhiAtVtxVsPosAbsEndMC); | |
1438 | ||
1439 | // --- diplay P*DCA --- | |
1440 | TCanvas* cPDCA = DrawVsAng("cPDCA", "p #times DCA in 3 angular regions", | |
1441 | static_cast<TH1*>(fTrackerList->UncheckedAt(kPDCA)), | |
1442 | static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsAngleAtAbsEnd))); | |
1443 | fDCAList->AddAt(cPDCA, kcPDCA); | |
1444 | TCanvas* cPDCAMC = DrawVsAng("cPDCAMC", "p #times DCA in 3 MC angular regions", | |
1445 | static_cast<TH1*>(fTrackerList->UncheckedAt(kPDCA)), | |
1446 | static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsMCAngle))); | |
1447 | fDCAList->AddAt(cPDCAMC, kcPDCAMC); | |
1448 | TCanvas* cPDCAVsPosAbsEndMC = DrawVsPos("cPDCAVsPosAbsEndMC", "p #times DCA versus position at absorber end in 3 MC angular regions", | |
1449 | static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsPosAbsEndIn02degMC)), | |
1450 | static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsPosAbsEndIn23degMC)), | |
1451 | static_cast<TH2*>(fTrackerList->UncheckedAt(kPDCAVsPosAbsEndIn310degMC))); | |
1452 | fDCAList->AddAt(cPDCAVsPosAbsEndMC, kcPDCAVsPosAbsEndMC); | |
1453 | ||
1454 | // post param containers | |
1455 | PostData(2, fEfficiencyList); | |
1456 | PostData(5, fPAtVtxList); | |
1457 | PostData(6, fSlopeAtVtxList); | |
1458 | PostData(7, fEtaAtVtxList); | |
1459 | PostData(8, fPhiAtVtxList); | |
1460 | PostData(9, fPAt1stClList); | |
1461 | PostData(10, fSlopeAt1stClList); | |
1462 | PostData(11, fDCAList); | |
1463 | PostData(12, fClusterList); | |
1464 | } | |
1465 | ||
1466 | ||
1467 | //________________________________________________________________________ | |
1468 | Bool_t AliAnalysisTaskMuonPerformance::GetEfficiency(AliCFEffGrid* efficiency, Double_t& calcEff, Double_t& calcEffErr) | |
1469 | { | |
1470 | // | |
1471 | /// Calculate the efficiency when cuts on the THnSparse are applied | |
1472 | // | |
1473 | ||
1474 | Bool_t isGood = kTRUE; | |
1475 | ||
1476 | TH1* histo = 0x0; | |
1477 | Double_t sum[2] = {0., 0.}; | |
1478 | for ( Int_t ihisto=0; ihisto<2; ihisto++ ) { | |
1479 | histo = ( ihisto==0 ) ? efficiency->GetNum()->Project(kVarCharge) : efficiency->GetDen()->Project(kVarCharge); | |
1480 | sum[ihisto] = histo->Integral(); | |
1481 | delete histo; | |
1482 | } | |
1483 | ||
1484 | if ( sum[1] == 0. ) isGood = kFALSE; | |
1485 | ||
1486 | calcEff = ( isGood ) ? sum[0]/sum[1] : 0.; | |
1487 | if ( calcEff > 1. ) isGood = kFALSE; | |
1488 | ||
1489 | calcEffErr = ( isGood ) ? TMath::Sqrt(calcEff*(1-calcEff)/sum[1]) : 0.; | |
1490 | ||
1491 | return isGood; | |
1492 | } | |
1493 | ||
1494 | //________________________________________________________________________ | |
1495 | Int_t AliAnalysisTaskMuonPerformance::RecoTrackMother(AliMCParticle* mcParticle) | |
1496 | { | |
1497 | // | |
1498 | /// Find track mother from kinematics | |
1499 | // | |
1500 | ||
1501 | if ( ! mcParticle ) | |
1502 | return kUnknownPart; | |
1503 | ||
1504 | Int_t recoPdg = mcParticle->PdgCode(); | |
1505 | ||
1506 | // Track is not a muon | |
1507 | if ( TMath::Abs(recoPdg) != 13 ) return kRecoHadron; | |
1508 | ||
1509 | Int_t imother = mcParticle->GetMother(); | |
1510 | ||
1511 | Bool_t isFirstMotherHF = kFALSE; | |
1512 | Int_t step = 0; | |
1513 | ||
1514 | //printf("\n"); // REMEMBER TO CUT | |
1515 | while ( imother >= 0 ) { | |
1516 | TParticle* part = static_cast<AliMCParticle*>(fMCEvent->GetTrack(imother))->Particle(); | |
1517 | //printf("Particle %s -> %s\n", part->GetName(), TMCProcessName[part->GetUniqueID()]); // REMEMBER TO CUT | |
1518 | ||
1519 | if ( part->GetUniqueID() == kPHadronic ) | |
1520 | return kSecondaryMu; | |
1521 | ||
1522 | Int_t absPdg = TMath::Abs(part->GetPdgCode()); | |
1523 | ||
1524 | step++; | |
1525 | if ( step == 1 ) // only for first mother | |
1526 | isFirstMotherHF = ( ( absPdg >= 400 && absPdg < 600 ) || | |
1527 | ( absPdg >= 4000 && absPdg < 6000 ) ); | |
1528 | ||
1529 | if ( absPdg < 4 ) | |
1530 | return kPrimaryMu; | |
1531 | ||
1532 | if ( isFirstMotherHF) { | |
1533 | if ( absPdg == 4 ) | |
1534 | return kCharmMu; | |
1535 | else if ( absPdg == 5 ) | |
1536 | return kBeautyMu; | |
1537 | } | |
1538 | ||
1539 | imother = part->GetFirstMother(); | |
1540 | } | |
1541 | ||
1542 | return kPrimaryMu; | |
1543 | ||
1544 | } | |
1545 | ||
1546 | //________________________________________________________________________ | |
1547 | Float_t AliAnalysisTaskMuonPerformance::GetBinThetaAbsEnd(Float_t RAtAbsEnd, Bool_t isTheta) | |
1548 | { | |
1549 | // | |
1550 | /// Get bin of theta at absorber end region | |
1551 | // | |
1552 | Float_t thetaDeg = ( isTheta ) ? RAtAbsEnd : TMath::ATan( RAtAbsEnd / 505. ); | |
1553 | thetaDeg *= TMath::RadToDeg(); | |
1554 | if ( thetaDeg < 2. ) | |
1555 | return 0.; | |
1556 | else if ( thetaDeg < 3. ) | |
1557 | return 1.; | |
1558 | else if ( thetaDeg < 9. ) | |
1559 | return 2.; | |
1560 | ||
1561 | return 3.; | |
1562 | } | |
1563 | ||
1564 | //________________________________________________________________________ | |
1565 | void AliAnalysisTaskMuonPerformance::FillContainerInfo(Double_t* containerInput, AliESDMuonTrack* esdTrack, Int_t mcID) | |
1566 | { | |
1567 | // | |
1568 | /// Fill container info (except kVarMatchMC) | |
1569 | // | |
1570 | ||
1571 | AliMCParticle* mcPart = 0x0; | |
1572 | if (mcID >= 0) mcPart = static_cast<AliMCParticle*>(fMCEvent->GetTrack(mcID)); | |
1573 | ||
1574 | AliVParticle* track = esdTrack; | |
1575 | if (!track) track = mcPart; | |
1576 | ||
e4249da8 | 1577 | if (track) { |
1578 | containerInput[kVarPt] = track->Pt(); | |
1579 | containerInput[kVarEta] = track->Eta(); | |
1580 | containerInput[kVarPhi] = track->Phi(); | |
1581 | containerInput[kVarThetaZones] = (esdTrack) ? GetBinThetaAbsEnd(esdTrack->GetRAtAbsorberEnd()) : GetBinThetaAbsEnd(TMath::Pi()-track->Theta(),kTRUE); | |
1582 | containerInput[kVarCharge] = (esdTrack) ? static_cast<Double_t>(track->Charge()) : static_cast<Double_t>(track->Charge())/3.; | |
1583 | containerInput[kVarHasTracker] = (esdTrack) ? static_cast<Double_t>(esdTrack->ContainTrackerData()) : 0.; | |
1584 | containerInput[kVarTrigger] = (esdTrack) ? static_cast<Double_t>(esdTrack->GetMatchTrigger()) : 0.; | |
1585 | containerInput[kVarMotherType] = static_cast<Double_t>(RecoTrackMother(mcPart)); | |
1586 | } | |
3c74311e | 1587 | |
1588 | if (esdTrack) esdTrack->SetLabel(mcID); | |
1589 | } | |
1590 | ||
1591 | //________________________________________________________________________ | |
1592 | Double_t langaufun(Double_t *x, Double_t *par) { | |
1593 | ||
1594 | //Fit parameters: | |
1595 | //par[0]=Width (scale) parameter of Landau density | |
1596 | //par[1]=Most Probable (MP, location) parameter of Landau density | |
1597 | //par[2]=Total area (integral -inf to inf, normalization constant) | |
1598 | //par[3]=Width (sigma) of convoluted Gaussian function | |
1599 | // | |
1600 | //In the Landau distribution (represented by the CERNLIB approximation), | |
1601 | //the maximum is located at x=-0.22278298 with the location parameter=0. | |
1602 | //This shift is corrected within this function, so that the actual | |
1603 | //maximum is identical to the MP parameter. | |
1604 | ||
1605 | // Numeric constants | |
1606 | Double_t invsq2pi = 0.3989422804014; // (2 pi)^(-1/2) | |
1607 | Double_t mpshift = -0.22278298; // Landau maximum location | |
1608 | ||
1609 | // Control constants | |
1610 | Double_t np = 100.0; // number of convolution steps | |
1611 | Double_t sc = 5.0; // convolution extends to +-sc Gaussian sigmas | |
1612 | ||
1613 | // Variables | |
1614 | Double_t xx; | |
1615 | Double_t mpc; | |
1616 | Double_t fland; | |
1617 | Double_t sum = 0.0; | |
1618 | Double_t xlow,xupp; | |
1619 | Double_t step; | |
1620 | Double_t i; | |
1621 | ||
1622 | ||
1623 | // MP shift correction | |
1624 | mpc = par[1] - mpshift * par[0]; | |
1625 | ||
1626 | // Range of convolution integral | |
1627 | xlow = x[0] - sc * par[3]; | |
1628 | xupp = x[0] + sc * par[3]; | |
1629 | ||
1630 | step = (xupp-xlow) / np; | |
1631 | ||
1632 | // Convolution integral of Landau and Gaussian by sum | |
1633 | for(i=1.0; i<=np/2; i++) { | |
1634 | xx = xlow + (i-.5) * step; | |
1635 | //change x -> -x because the tail of the Landau is at the left here... | |
1636 | fland = TMath::Landau(-xx,mpc,par[0]) / par[0]; | |
1637 | sum += fland * TMath::Gaus(x[0],xx,par[3]); | |
1638 | ||
1639 | //change x -> -x because the tail of the Landau is at the left here... | |
1640 | xx = xupp - (i-.5) * step; | |
1641 | fland = TMath::Landau(-xx,mpc,par[0]) / par[0]; | |
1642 | sum += fland * TMath::Gaus(x[0],xx,par[3]); | |
1643 | } | |
1644 | ||
1645 | return (par[2] * step * sum * invsq2pi / par[3]); | |
1646 | } | |
1647 | ||
1648 | //________________________________________________________________________ | |
1649 | void AliAnalysisTaskMuonPerformance::FitLandauGausResVsP(TH2* h, const char* fitting, TGraphAsymmErrors* gMean, | |
1650 | TGraphAsymmErrors* gMostProb, TGraphAsymmErrors* gSigma) | |
1651 | { | |
1652 | /// generic function to fit residuals versus momentum with a landau convoluted with a gaussian | |
1653 | ||
1654 | static TF1* fLandauGaus = 0x0; | |
1655 | if (!fLandauGaus) fLandauGaus = new TF1("fLandauGaus",langaufun,h->GetYaxis()->GetBinLowEdge(1),h->GetYaxis()->GetBinLowEdge(h->GetNbinsY()+1),4); | |
1656 | ||
1657 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/fNPBins, 1); | |
1658 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1659 | ||
1660 | cout<<Form("\rFitting %s... %d/%d",fitting,i/rebinFactorX,fNPBins)<<flush; | |
1661 | ||
1662 | TH1D *tmp = h->ProjectionY("tmp",i-rebinFactorX+1,i,"e"); | |
1663 | ||
1664 | // first fit | |
1665 | fLandauGaus->SetParameters(0.2,0.,(Double_t)tmp->GetEntries(),1.); | |
1666 | tmp->Fit("fLandauGaus","WWNQ"); | |
1667 | ||
1668 | // rebin histo | |
1669 | Double_t fwhm = fLandauGaus->GetParameter(0); | |
1670 | Double_t sigma = fLandauGaus->GetParameter(3); | |
1671 | Double_t sigmaP = TMath::Sqrt(sigma*sigma + fwhm*fwhm/(8.*log(2.))); | |
1672 | Int_t rebin = TMath::Max(static_cast<Int_t>(0.5*sigmaP/tmp->GetBinWidth(1)),1); | |
1673 | while (tmp->GetNbinsX()%rebin!=0) rebin--; | |
1674 | tmp->Rebin(rebin); | |
1675 | ||
1676 | // second fit | |
1677 | tmp->Fit("fLandauGaus","NQ"); | |
1678 | ||
1679 | // get fit results and fill histograms | |
1680 | fwhm = fLandauGaus->GetParameter(0); | |
1681 | sigma = fLandauGaus->GetParameter(3); | |
1682 | sigmaP = TMath::Sqrt(sigma*sigma + fwhm*fwhm/(8.*log(2.))); | |
1683 | Double_t fwhmErr = fLandauGaus->GetParError(0); | |
1684 | Double_t sigmaErr = fLandauGaus->GetParError(3); | |
1685 | Double_t sigmaPErr = TMath::Sqrt(sigma*sigma*sigmaErr*sigmaErr + fwhm*fwhm*fwhmErr*fwhmErr/(64.*log(2.)*log(2.))) / sigmaP; | |
1686 | h->GetXaxis()->SetRange(i-rebinFactorX+1,i); | |
1687 | Double_t p = (tmp->GetEntries() > 0) ? h->GetMean() : 0.5 * (h->GetBinLowEdge(i-rebinFactorX+1) + h->GetBinLowEdge(i+1)); | |
1688 | h->GetXaxis()->SetRange(); | |
1689 | Double_t pErr[2] = {p-h->GetBinLowEdge(i-rebinFactorX+1), h->GetBinLowEdge(i+1)-p}; | |
1690 | gMean->SetPoint(i/rebinFactorX-1, p, tmp->GetMean()); | |
1691 | gMean->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], tmp->GetMeanError(), tmp->GetMeanError()); | |
1692 | gMostProb->SetPoint(i/rebinFactorX-1, p, -fLandauGaus->GetParameter(1)); | |
1693 | gMostProb->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], fLandauGaus->GetParError(1), fLandauGaus->GetParError(1)); | |
1694 | gSigma->SetPoint(i/rebinFactorX-1, p, sigmaP); | |
1695 | gSigma->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], sigmaPErr, sigmaPErr); | |
1696 | ||
1697 | // clean memory | |
1698 | delete tmp; | |
1699 | } | |
1700 | ||
1701 | cout<<Form("\rFitting %s... %d/%d",fitting,fNPBins,fNPBins)<<endl; | |
1702 | ||
1703 | } | |
1704 | ||
1705 | //________________________________________________________________________ | |
1706 | void AliAnalysisTaskMuonPerformance::FitGausResVsMom(TH2* h, const Double_t mean0, | |
1707 | const Double_t sigma0, const char* fitting, | |
1708 | TGraphAsymmErrors* gMean, TGraphAsymmErrors* gSigma) | |
1709 | { | |
1710 | /// generic function to fit residuals versus momentum with a gaussian | |
1711 | ||
1712 | static TF1* fGaus = 0x0; | |
1713 | if (!fGaus) fGaus = new TF1("fGaus","gaus"); | |
1714 | ||
1715 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/fNPBins, 1); | |
1716 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1717 | ||
1718 | cout<<Form("\rFitting %s... %d/%d",fitting,i/rebinFactorX,fNPBins)<<flush; | |
1719 | ||
1720 | TH1D *tmp = h->ProjectionY("tmp",i-rebinFactorX+1,i,"e"); | |
1721 | ||
1722 | // first fit | |
1723 | fGaus->SetParameters(tmp->GetEntries(), mean0, sigma0); | |
1724 | tmp->Fit("fGaus","WWNQ"); | |
1725 | ||
1726 | // rebin histo | |
1727 | Int_t rebin = TMath::Max(static_cast<Int_t>(0.5*fGaus->GetParameter(2)/tmp->GetBinWidth(1)),1); | |
1728 | while (tmp->GetNbinsX()%rebin!=0) rebin--; | |
1729 | tmp->Rebin(rebin); | |
1730 | ||
1731 | // second fit | |
1732 | tmp->Fit("fGaus","NQ"); | |
1733 | ||
1734 | // get fit results and fill histograms | |
1735 | h->GetXaxis()->SetRange(i-rebinFactorX+1,i); | |
1736 | Double_t p = (tmp->GetEntries() > 0) ? h->GetMean() : 0.5 * (h->GetBinLowEdge(i-rebinFactorX+1) + h->GetBinLowEdge(i+1)); | |
1737 | h->GetXaxis()->SetRange(); | |
1738 | Double_t pErr[2] = {p-h->GetBinLowEdge(i-rebinFactorX+1), h->GetBinLowEdge(i+1)-p}; | |
1739 | gMean->SetPoint(i/rebinFactorX-1, p, fGaus->GetParameter(1)); | |
1740 | gMean->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], fGaus->GetParError(1), fGaus->GetParError(1)); | |
1741 | gSigma->SetPoint(i/rebinFactorX-1, p, fGaus->GetParameter(2)); | |
1742 | gSigma->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], fGaus->GetParError(2), fGaus->GetParError(2)); | |
1743 | ||
1744 | // clean memory | |
1745 | delete tmp; | |
1746 | } | |
1747 | ||
1748 | cout<<Form("\rFitting %s... %d/%d",fitting,fNPBins,fNPBins)<<endl; | |
1749 | ||
1750 | } | |
1751 | ||
1752 | //________________________________________________________________________ | |
1753 | void AliAnalysisTaskMuonPerformance::FitPDCAVsMom(TH2* h, const char* fitting, | |
1754 | TGraphAsymmErrors* gMean, TGraphAsymmErrors* gSigma) | |
1755 | { | |
1756 | /// generic function to fit p*DCA distributions | |
1757 | ||
1758 | static TF1* fPGaus = 0x0; | |
1759 | if (!fPGaus) fPGaus = new TF1("fPGaus","x*gaus"); | |
1760 | ||
1761 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/fNPBins, 1); | |
1762 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1763 | ||
1764 | cout<<Form("\rFitting %s... %d/%d",fitting,i/rebinFactorX,fNPBins)<<flush; | |
1765 | ||
1766 | TH1D *tmp = h->ProjectionY("tmp",i-rebinFactorX+1,i,"e"); | |
1767 | ||
1768 | // rebin histo | |
1769 | Int_t rebin = static_cast<Int_t>(25*(tmp->GetNbinsX()/(tmp->GetBinLowEdge(tmp->GetNbinsX()+1)-tmp->GetBinLowEdge(1)))); | |
1770 | while (tmp->GetNbinsX()%rebin!=0) rebin--; | |
1771 | tmp->Rebin(rebin); | |
1772 | ||
1773 | // fit | |
1774 | fPGaus->SetParameters(1.,0.,80.); | |
1775 | tmp->Fit("fPGaus","NQ"); | |
1776 | ||
1777 | // get fit results and fill histograms | |
1778 | h->GetXaxis()->SetRange(i-rebinFactorX+1,i); | |
1779 | Double_t p = (tmp->GetEntries() > 0) ? h->GetMean() : 0.5 * (h->GetBinLowEdge(i-rebinFactorX+1) + h->GetBinLowEdge(i+1)); | |
1780 | h->GetXaxis()->SetRange(); | |
1781 | Double_t pErr[2] = {p-h->GetBinLowEdge(i-rebinFactorX+1), h->GetBinLowEdge(i+1)-p}; | |
1782 | gMean->SetPoint(i/rebinFactorX-1, p, fPGaus->GetParameter(1)); | |
1783 | gMean->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], fPGaus->GetParError(1), fPGaus->GetParError(1)); | |
1784 | gSigma->SetPoint(i/rebinFactorX-1, p, fPGaus->GetParameter(2)); | |
1785 | gSigma->SetPointError(i/rebinFactorX-1, pErr[0], pErr[1], fPGaus->GetParError(2), fPGaus->GetParError(2)); | |
1786 | ||
1787 | // clean memory | |
1788 | delete tmp; | |
1789 | } | |
1790 | ||
1791 | cout<<Form("\rFitting %s... %d/%d",fitting,fNPBins,fNPBins)<<endl; | |
1792 | ||
1793 | } | |
1794 | ||
1795 | //________________________________________________________________________ | |
1796 | void AliAnalysisTaskMuonPerformance::FitClusterResidual(TH1* h, Int_t i, Double_t& sigma, | |
1797 | TGraphErrors* gMean, TGraphErrors* gSigma) | |
1798 | { | |
1799 | /// fill graphs with residual mean and sigma | |
1800 | ||
1801 | static TF1* fRGaus = 0x0; | |
1802 | Double_t mean, meanErr, sigmaErr; | |
1803 | ||
1804 | if (fFitResiduals) { | |
1805 | ||
1806 | if (!fRGaus) fRGaus = new TF1("fRGaus","gaus"); | |
1807 | ||
1808 | // first fit | |
1809 | fRGaus->SetParameters(h->GetEntries(), 0., 0.1); | |
1810 | h->Fit("fRGaus", "WWNQ"); | |
1811 | ||
1812 | // rebin histo | |
1813 | Int_t rebin = TMath::Max(static_cast<Int_t>(0.2*fRGaus->GetParameter(2)/h->GetBinWidth(1)),1); | |
1814 | while (h->GetNbinsX()%rebin!=0) rebin--; | |
1815 | h->Rebin(rebin); | |
1816 | ||
1817 | // second fit | |
1818 | h->Fit("fRGaus","NQ"); | |
1819 | ||
1820 | mean = fRGaus->GetParameter(1); | |
1821 | meanErr = fRGaus->GetParError(1); | |
1822 | sigma = fRGaus->GetParameter(2); | |
1823 | sigmaErr = fRGaus->GetParError(2); | |
1824 | ||
1825 | } else { | |
1826 | ||
1827 | Zoom(h); | |
1828 | mean = h->GetMean(); | |
1829 | meanErr = h->GetMeanError(); | |
1830 | sigma = h->GetRMS(); | |
1831 | sigmaErr = h->GetRMSError(); | |
1832 | h->GetXaxis()->SetRange(0,0); | |
1833 | ||
1834 | } | |
1835 | ||
1836 | gMean->SetPoint(i, i+1, mean); | |
1837 | gMean->SetPointError(i, 0., meanErr); | |
1838 | ||
1839 | if (fCorrectForSystematics) { | |
1840 | Double_t s = TMath::Sqrt(mean*mean + sigma*sigma); | |
1841 | sigmaErr = (s>0.) ? TMath::Sqrt(sigma*sigma*sigmaErr*sigmaErr + mean*mean*meanErr*meanErr) / s : 0.; | |
1842 | sigma = s; | |
1843 | } | |
1844 | ||
1845 | gSigma->SetPoint(i, i+1, sigma); | |
1846 | gSigma->SetPointError(i, 0., sigmaErr); | |
1847 | ||
1848 | } | |
1849 | ||
1850 | //________________________________________________________________________ | |
1851 | TCanvas* AliAnalysisTaskMuonPerformance::DrawVsAng(const char* name, const char* title, TH1* h1, TH2* h2) | |
1852 | { | |
1853 | /// generic function to draw histograms versus absorber angular region | |
1854 | TCanvas* c = new TCanvas(name, title); | |
1855 | c->cd(); | |
1856 | h1->DrawCopy(); | |
1857 | TH1D *proj1 = h2->ProjectionY(Form("%s_proj_0_2",h2->GetName()),1,2); | |
1858 | proj1->SetLineColor(2); | |
1859 | proj1->Draw("sames"); | |
1860 | TH1D *proj2 = h2->ProjectionY(Form("%s_proj_2_3",h2->GetName()),3,3); | |
1861 | proj2->SetLineColor(4); | |
1862 | proj2->Draw("sames"); | |
1863 | TH1D *proj3 = h2->ProjectionY(Form("%s__proj_3_10",h2->GetName()),4,10); | |
1864 | proj3->SetLineColor(3); | |
1865 | proj3->Draw("sames"); | |
1866 | return c; | |
1867 | } | |
1868 | ||
1869 | //________________________________________________________________________ | |
1870 | TCanvas* AliAnalysisTaskMuonPerformance::DrawVsPos(const char* name, const char* title, TH2* h1, TH2* h2, TH2* h3) | |
1871 | { | |
1872 | /// generic function to draw histograms versus position at absorber end | |
1873 | TCanvas* c = new TCanvas(name, title); | |
1874 | c->cd(); | |
1875 | h1->SetMarkerColor(2); | |
1876 | h1->DrawCopy(); | |
1877 | h2->SetMarkerColor(4); | |
1878 | h2->DrawCopy("sames"); | |
1879 | h3->SetMarkerColor(3); | |
1880 | h3->DrawCopy("sames"); | |
1881 | return c; | |
1882 | } | |
1883 | ||
1884 | //________________________________________________________________________ | |
1885 | TCanvas* AliAnalysisTaskMuonPerformance::DrawFitLandauGausResPVsP(const char* name, const char* title, | |
1886 | TH2* h, const Int_t nBins, const char* fitting) | |
1887 | { | |
1888 | /// generic function to draw and fit momentum residuals versus momentum | |
1889 | ||
1890 | static TF1* fLandauGaus = 0x0; | |
1891 | if (!fLandauGaus) fLandauGaus = new TF1("fLandauGaus",langaufun,h->GetYaxis()->GetBinLowEdge(1),h->GetYaxis()->GetBinLowEdge(h->GetNbinsY()+1),4); | |
1892 | ||
1893 | TLegend* l = new TLegend(0.15,0.25,0.3,0.85); | |
1894 | TCanvas* c = new TCanvas(name, title); | |
1895 | c->cd(); | |
1896 | ||
1897 | h->Sumw2(); | |
1898 | ||
1899 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/nBins, 1); | |
1900 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1901 | ||
1902 | cout<<Form("\rFitting %s... %d/%d",fitting,i/rebinFactorX,nBins)<<flush; | |
1903 | ||
1904 | // draw projection | |
1905 | TH1D* proj = h->ProjectionY(Form("%s_%d",h->GetName(),i/rebinFactorX),i-rebinFactorX+1,i); | |
1906 | if (proj->GetEntries() > 0) proj->Scale(1./proj->GetEntries()); | |
1907 | proj->Draw((i==rebinFactorX)?"hist":"histsames"); | |
1908 | proj->SetLineColor(i/rebinFactorX); | |
1909 | ||
1910 | // first fit | |
1911 | fLandauGaus->SetParameters(0.2,0.,1.,1.); | |
1912 | fLandauGaus->SetLineColor(i/rebinFactorX); | |
1913 | proj->Fit("fLandauGaus","WWNQ","sames"); | |
1914 | ||
1915 | // rebin histo | |
1916 | Double_t fwhm = fLandauGaus->GetParameter(0); | |
1917 | Double_t sigma = fLandauGaus->GetParameter(3); | |
1918 | Double_t sigmaP = TMath::Sqrt(sigma*sigma + fwhm*fwhm/(8.*log(2.))); | |
1919 | Int_t rebin = TMath::Max(static_cast<Int_t>(0.5*sigmaP/proj->GetBinWidth(1)),1); | |
1920 | while (proj->GetNbinsX()%rebin!=0) rebin--; | |
1921 | proj->Rebin(rebin); | |
1922 | proj->Scale(1./rebin); | |
1923 | ||
1924 | // second fit | |
1925 | proj->Fit("fLandauGaus","Q","sames"); | |
1926 | ||
1927 | // set label | |
1928 | Double_t p = 0.5 * (h->GetBinLowEdge(i-rebinFactorX+1) + h->GetBinLowEdge(i+1)); | |
1929 | l->AddEntry(proj,Form("%5.1f GeV",p)); | |
1930 | ||
1931 | } | |
1932 | ||
1933 | cout<<Form("\rFitting %s... %d/%d",fitting,nBins,nBins)<<endl; | |
1934 | ||
1935 | l->Draw("same"); | |
1936 | ||
1937 | return c; | |
1938 | } | |
1939 | ||
1940 | //________________________________________________________________________ | |
1941 | TCanvas* AliAnalysisTaskMuonPerformance::DrawResPVsP(const char* name, const char* title, TH2* h, const Int_t nBins) | |
1942 | { | |
1943 | /// generic function to draw momentum residuals versus momentum | |
1944 | ||
1945 | TLegend* l = new TLegend(0.15,0.25,0.3,0.85); | |
1946 | TCanvas* c = new TCanvas(name, title); | |
1947 | c->cd(); | |
1948 | ||
1949 | h->Sumw2(); | |
1950 | ||
1951 | Int_t rebinFactorX = TMath::Max(h->GetNbinsX()/nBins, 1); | |
1952 | for (Int_t i = rebinFactorX; i <= h->GetNbinsX(); i+=rebinFactorX) { | |
1953 | ||
1954 | // draw projection | |
1955 | TH1D* proj = h->ProjectionY(Form("%s_%d",h->GetName(),i/rebinFactorX),i-rebinFactorX+1,i); | |
1956 | if (proj->GetEntries() > 0) proj->Scale(1./proj->GetEntries()); | |
1957 | proj->Draw((i==rebinFactorX)?"hist":"histsames"); | |
1958 | proj->SetLineColor(i/rebinFactorX); | |
1959 | proj->SetLineWidth(2); | |
1960 | ||
1961 | // set label | |
1962 | Double_t p = 0.5 * (h->GetBinLowEdge(i-rebinFactorX+1) + h->GetBinLowEdge(i+1)); | |
1963 | l->AddEntry(proj,Form("%5.1f GeV",p)); | |
1964 | ||
1965 | } | |
1966 | ||
1967 | l->Draw("same"); | |
1968 | ||
1969 | return c; | |
1970 | } | |
1971 | ||
1972 | //________________________________________________________________________ | |
1973 | void AliAnalysisTaskMuonPerformance::Zoom(TH1* h, Double_t fractionCut) | |
1974 | { | |
1975 | /// Reduce the range of the histogram by removing a given fration of the statistic at each edge | |
1976 | ||
1977 | Double_t maxEventsCut = fractionCut * h->GetEntries(); | |
1978 | Int_t nBins = h->GetNbinsX(); | |
1979 | ||
1980 | // set low edge | |
1981 | Int_t minBin; | |
1982 | Double_t eventsCut = 0.; | |
1983 | for (minBin = 1; minBin <= nBins; minBin++) { | |
1984 | eventsCut += h->GetBinContent(minBin); | |
1985 | if (eventsCut > maxEventsCut) break; | |
1986 | } | |
1987 | ||
1988 | // set high edge | |
1989 | Int_t maxBin; | |
1990 | eventsCut = 0.; | |
1991 | for (maxBin = nBins; maxBin >= 1; maxBin--) { | |
1992 | eventsCut += h->GetBinContent(maxBin); | |
1993 | if (eventsCut > maxEventsCut) break; | |
1994 | } | |
1995 | ||
1996 | // set new axis range | |
1997 | h->GetXaxis()->SetRange(--minBin, ++maxBin); | |
1998 | } |