1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
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 **************************************************************************/
16 /* $Id: AliESDtrackCuts.cxx 24534 2008-03-16 22:22:11Z fca $ */
18 #include "AliESDtrackCuts.h"
20 #include <AliESDtrack.h>
21 #include <AliESDVertex.h>
22 #include <AliESDEvent.h>
23 #include <AliMultiplicity.h>
28 #include <TDirectory.h>
32 //____________________________________________________________________
33 ClassImp(AliESDtrackCuts)
36 const Char_t* AliESDtrackCuts::fgkCutNames[kNCuts] = {
38 "require TPC standalone",
42 "#Chi^{2}/cluster TPC",
43 "#Chi^{2}/cluster ITS",
59 "trk-to-vtx max dca 2D absolute",
60 "trk-to-vtx max dca xy absolute",
61 "trk-to-vtx max dca z absolute",
62 "trk-to-vtx min dca 2D absolute",
63 "trk-to-vtx min dca xy absolute",
64 "trk-to-vtx min dca z absolute",
65 "SPD cluster requirement",
66 "SDD cluster requirement",
67 "SSD cluster requirement",
68 "require ITS stand-alone",
69 "rel 1/pt uncertainty",
70 "TPC n shared clusters",
71 "TPC rel shared clusters",
74 "n crossed rows / n findable clusters",
76 "#Chi^{2} TPC constrained vs. global"
79 AliESDtrackCuts* AliESDtrackCuts::fgMultEstTrackCuts[AliESDtrackCuts::kNMultEstTrackCuts] = { 0, 0, 0, 0 };
81 //____________________________________________________________________
82 AliESDtrackCuts::AliESDtrackCuts(const Char_t* name, const Char_t* title) : AliAnalysisCuts(name,title),
83 fCutMinNClusterTPC(0),
84 fCutMinNClusterITS(0),
85 fCutMinNCrossedRowsTPC(0),
86 fCutMinRatioCrossedRowsOverFindableClustersTPC(0),
87 f1CutMinNClustersTPCPtDep(0x0),
88 fCutMaxPtDepNClustersTPC(0),
89 fCutMaxChi2PerClusterTPC(0),
90 fCutMaxChi2PerClusterITS(0),
91 fCutMaxChi2TPCConstrainedVsGlobal(0),
92 fCutMaxChi2TPCConstrainedVsGlobalVertexType(kVertexTracks | kVertexSPD),
93 fCutMaxMissingITSPoints(0),
99 fCutMaxRel1PtUncertainty(0),
100 fCutAcceptKinkDaughters(0),
101 fCutAcceptSharedTPCClusters(0),
102 fCutMaxFractionSharedTPCClusters(0),
103 fCutRequireTPCRefit(0),
104 fCutRequireTPCStandAlone(0),
105 fCutRequireITSRefit(0),
106 fCutRequireITSPid(0),
107 fCutRequireITSStandAlone(0),
108 fCutRequireITSpureSA(0),
109 fCutNsigmaToVertex(0),
110 fCutSigmaToVertexRequired(0),
111 fCutMaxDCAToVertexXY(0),
112 fCutMaxDCAToVertexZ(0),
113 fCutMinDCAToVertexXY(0),
114 fCutMinDCAToVertexZ(0),
115 fCutMaxDCAToVertexXYPtDep(""),
116 fCutMaxDCAToVertexZPtDep(""),
117 fCutMinDCAToVertexXYPtDep(""),
118 fCutMinDCAToVertexZPtDep(""),
119 f1CutMaxDCAToVertexXYPtDep(0x0),
120 f1CutMaxDCAToVertexZPtDep(0x0),
121 f1CutMinDCAToVertexXYPtDep(0x0),
122 f1CutMinDCAToVertexZPtDep(0x0),
123 fCutDCAToVertex2D(0),
149 //##############################################################################
150 // setting default cuts
151 SetMinNClustersTPC();
152 SetMinNClustersITS();
153 SetMinNCrossedRowsTPC();
154 SetMinRatioCrossedRowsOverFindableClustersTPC();
155 SetMaxChi2PerClusterTPC();
156 SetMaxChi2PerClusterITS();
157 SetMaxChi2TPCConstrainedGlobal();
158 SetMaxChi2TPCConstrainedGlobalVertexType();
159 SetMaxNOfMissingITSPoints();
160 SetMaxCovDiagonalElements();
161 SetMaxRel1PtUncertainty();
162 SetRequireTPCRefit();
163 SetRequireTPCStandAlone();
164 SetRequireITSRefit();
165 SetRequireITSPid(kFALSE);
166 SetRequireITSStandAlone(kFALSE);
167 SetRequireITSPureStandAlone(kFALSE);
168 SetAcceptKinkDaughters();
169 SetAcceptSharedTPCClusters();
170 SetMaxFractionSharedTPCClusters();
171 SetMaxNsigmaToVertex();
172 SetMaxDCAToVertexXY();
173 SetMaxDCAToVertexZ();
175 SetMinDCAToVertexXY();
176 SetMinDCAToVertexZ();
184 SetClusterRequirementITS(kSPD);
185 SetClusterRequirementITS(kSDD);
186 SetClusterRequirementITS(kSSD);
191 //_____________________________________________________________________________
192 AliESDtrackCuts::AliESDtrackCuts(const AliESDtrackCuts &c) : AliAnalysisCuts(c),
193 fCutMinNClusterTPC(0),
194 fCutMinNClusterITS(0),
195 fCutMinNCrossedRowsTPC(0),
196 fCutMinRatioCrossedRowsOverFindableClustersTPC(0),
197 f1CutMinNClustersTPCPtDep(0x0),
198 fCutMaxPtDepNClustersTPC(0),
199 fCutMaxChi2PerClusterTPC(0),
200 fCutMaxChi2PerClusterITS(0),
201 fCutMaxChi2TPCConstrainedVsGlobal(0),
202 fCutMaxChi2TPCConstrainedVsGlobalVertexType(kVertexTracks | kVertexSPD),
203 fCutMaxMissingITSPoints(0),
209 fCutMaxRel1PtUncertainty(0),
210 fCutAcceptKinkDaughters(0),
211 fCutAcceptSharedTPCClusters(0),
212 fCutMaxFractionSharedTPCClusters(0),
213 fCutRequireTPCRefit(0),
214 fCutRequireTPCStandAlone(0),
215 fCutRequireITSRefit(0),
216 fCutRequireITSPid(0),
217 fCutRequireITSStandAlone(0),
218 fCutRequireITSpureSA(0),
219 fCutNsigmaToVertex(0),
220 fCutSigmaToVertexRequired(0),
221 fCutMaxDCAToVertexXY(0),
222 fCutMaxDCAToVertexZ(0),
223 fCutMinDCAToVertexXY(0),
224 fCutMinDCAToVertexZ(0),
225 fCutMaxDCAToVertexXYPtDep(""),
226 fCutMaxDCAToVertexZPtDep(""),
227 fCutMinDCAToVertexXYPtDep(""),
228 fCutMinDCAToVertexZPtDep(""),
229 f1CutMaxDCAToVertexXYPtDep(0x0),
230 f1CutMaxDCAToVertexZPtDep(0x0),
231 f1CutMinDCAToVertexXYPtDep(0x0),
232 f1CutMinDCAToVertexZPtDep(0x0),
233 fCutDCAToVertex2D(0),
257 ((AliESDtrackCuts &) c).Copy(*this);
260 AliESDtrackCuts::~AliESDtrackCuts()
266 for (Int_t i=0; i<2; i++) {
268 if (fhNClustersITS[i])
269 delete fhNClustersITS[i];
270 if (fhNClustersTPC[i])
271 delete fhNClustersTPC[i];
272 if (fhNSharedClustersTPC[i])
273 delete fhNSharedClustersTPC[i];
274 if (fhNCrossedRowsTPC[i])
275 delete fhNCrossedRowsTPC[i];
276 if (fhRatioCrossedRowsOverFindableClustersTPC[i])
277 delete fhRatioCrossedRowsOverFindableClustersTPC[i];
278 if (fhChi2PerClusterITS[i])
279 delete fhChi2PerClusterITS[i];
280 if (fhChi2PerClusterTPC[i])
281 delete fhChi2PerClusterTPC[i];
282 if (fhChi2TPCConstrainedVsGlobal[i])
283 delete fhChi2TPCConstrainedVsGlobal[i];
284 if(fhNClustersForITSPID[i])
285 delete fhNClustersForITSPID[i];
286 if(fhNMissingITSPoints[i])
287 delete fhNMissingITSPoints[i];
299 if (fhRel1PtUncertainty[i])
300 delete fhRel1PtUncertainty[i];
311 if (fhDXYNormalized[i])
312 delete fhDXYNormalized[i];
313 if (fhDZNormalized[i])
314 delete fhDZNormalized[i];
315 if (fhDXYvsDZNormalized[i])
316 delete fhDXYvsDZNormalized[i];
317 if (fhNSigmaToVertex[i])
318 delete fhNSigmaToVertex[i];
325 if(f1CutMaxDCAToVertexXYPtDep)delete f1CutMaxDCAToVertexXYPtDep;
326 f1CutMaxDCAToVertexXYPtDep = 0;
327 if( f1CutMaxDCAToVertexZPtDep) delete f1CutMaxDCAToVertexZPtDep;
328 f1CutMaxDCAToVertexZPtDep = 0;
329 if( f1CutMinDCAToVertexXYPtDep)delete f1CutMinDCAToVertexXYPtDep;
330 f1CutMinDCAToVertexXYPtDep = 0;
331 if(f1CutMinDCAToVertexZPtDep)delete f1CutMinDCAToVertexZPtDep;
332 f1CutMinDCAToVertexZPtDep = 0;
336 delete ffDTheoretical;
339 delete fhCutStatistics;
340 if (fhCutCorrelation)
341 delete fhCutCorrelation;
343 if(f1CutMinNClustersTPCPtDep)
344 delete f1CutMinNClustersTPCPtDep;
348 void AliESDtrackCuts::Init()
351 // sets everything to zero
354 fCutMinNClusterTPC = 0;
355 fCutMinNClusterITS = 0;
357 fCutMaxChi2PerClusterTPC = 0;
358 fCutMaxChi2PerClusterITS = 0;
359 fCutMaxChi2TPCConstrainedVsGlobal = 0;
360 fCutMaxChi2TPCConstrainedVsGlobalVertexType = kVertexTracks | kVertexSPD;
361 fCutMaxMissingITSPoints = 0;
363 for (Int_t i = 0; i < 3; i++)
364 fCutClusterRequirementITS[i] = kOff;
372 fCutMaxRel1PtUncertainty = 0;
374 fCutAcceptKinkDaughters = 0;
375 fCutAcceptSharedTPCClusters = 0;
376 fCutMaxFractionSharedTPCClusters = 0;
377 fCutRequireTPCRefit = 0;
378 fCutRequireTPCStandAlone = 0;
379 fCutRequireITSRefit = 0;
380 fCutRequireITSPid = 0;
381 fCutRequireITSStandAlone = 0;
382 fCutRequireITSpureSA = 0;
384 fCutNsigmaToVertex = 0;
385 fCutSigmaToVertexRequired = 0;
386 fCutMaxDCAToVertexXY = 0;
387 fCutMaxDCAToVertexZ = 0;
388 fCutDCAToVertex2D = 0;
389 fCutMinDCAToVertexXY = 0;
390 fCutMinDCAToVertexZ = 0;
391 fCutMaxDCAToVertexXYPtDep = "";
392 fCutMaxDCAToVertexZPtDep = "";
393 fCutMinDCAToVertexXYPtDep = "";
394 fCutMinDCAToVertexZPtDep = "";
396 if(f1CutMaxDCAToVertexXYPtDep)delete f1CutMaxDCAToVertexXYPtDep;
397 f1CutMaxDCAToVertexXYPtDep = 0;
398 if( f1CutMaxDCAToVertexXYPtDep) delete f1CutMaxDCAToVertexXYPtDep;
399 f1CutMaxDCAToVertexXYPtDep = 0;
400 if( f1CutMaxDCAToVertexZPtDep) delete f1CutMaxDCAToVertexZPtDep;
401 f1CutMaxDCAToVertexZPtDep = 0;
402 if( f1CutMinDCAToVertexXYPtDep)delete f1CutMinDCAToVertexXYPtDep;
403 f1CutMinDCAToVertexXYPtDep = 0;
404 if(f1CutMinDCAToVertexZPtDep)delete f1CutMinDCAToVertexZPtDep;
405 f1CutMinDCAToVertexZPtDep = 0;
423 fHistogramsOn = kFALSE;
425 for (Int_t i=0; i<2; ++i)
427 fhNClustersITS[i] = 0;
428 fhNClustersTPC[i] = 0;
429 fhNSharedClustersTPC[i] = 0;
430 fhNCrossedRowsTPC[i] = 0;
431 fhRatioCrossedRowsOverFindableClustersTPC[i] = 0;
433 fhChi2PerClusterITS[i] = 0;
434 fhChi2PerClusterTPC[i] = 0;
435 fhChi2TPCConstrainedVsGlobal[i] = 0;
436 fhNClustersForITSPID[i] = 0;
437 fhNMissingITSPoints[i] = 0;
445 fhRel1PtUncertainty[i] = 0;
452 fhDXYNormalized[i] = 0;
453 fhDZNormalized[i] = 0;
454 fhDXYvsDZNormalized[i] = 0;
455 fhNSigmaToVertex[i] = 0;
463 fhCutCorrelation = 0;
466 //_____________________________________________________________________________
467 AliESDtrackCuts &AliESDtrackCuts::operator=(const AliESDtrackCuts &c)
470 // Assignment operator
473 if (this != &c) ((AliESDtrackCuts &) c).Copy(*this);
477 //_____________________________________________________________________________
478 void AliESDtrackCuts::Copy(TObject &c) const
484 AliESDtrackCuts& target = (AliESDtrackCuts &) c;
488 target.fCutMinNClusterTPC = fCutMinNClusterTPC;
489 target.fCutMinNClusterITS = fCutMinNClusterITS;
490 target.fCutMinNCrossedRowsTPC = fCutMinNCrossedRowsTPC;
491 target.fCutMinRatioCrossedRowsOverFindableClustersTPC = fCutMinRatioCrossedRowsOverFindableClustersTPC;
492 if(f1CutMinNClustersTPCPtDep){
493 target.f1CutMinNClustersTPCPtDep = (TFormula*) f1CutMinNClustersTPCPtDep->Clone("f1CutMinNClustersTPCPtDep");
495 target.fCutMaxPtDepNClustersTPC = fCutMaxPtDepNClustersTPC;
497 target.fCutMaxChi2PerClusterTPC = fCutMaxChi2PerClusterTPC;
498 target.fCutMaxChi2PerClusterITS = fCutMaxChi2PerClusterITS;
499 target.fCutMaxChi2TPCConstrainedVsGlobal = fCutMaxChi2TPCConstrainedVsGlobal;
500 target.fCutMaxChi2TPCConstrainedVsGlobalVertexType = fCutMaxChi2TPCConstrainedVsGlobalVertexType;
501 target.fCutMaxMissingITSPoints = fCutMaxMissingITSPoints;
503 for (Int_t i = 0; i < 3; i++)
504 target.fCutClusterRequirementITS[i] = fCutClusterRequirementITS[i];
506 target.fCutMaxC11 = fCutMaxC11;
507 target.fCutMaxC22 = fCutMaxC22;
508 target.fCutMaxC33 = fCutMaxC33;
509 target.fCutMaxC44 = fCutMaxC44;
510 target.fCutMaxC55 = fCutMaxC55;
512 target.fCutMaxRel1PtUncertainty = fCutMaxRel1PtUncertainty;
514 target.fCutAcceptKinkDaughters = fCutAcceptKinkDaughters;
515 target.fCutAcceptSharedTPCClusters = fCutAcceptSharedTPCClusters;
516 target.fCutMaxFractionSharedTPCClusters = fCutMaxFractionSharedTPCClusters;
517 target.fCutRequireTPCRefit = fCutRequireTPCRefit;
518 target.fCutRequireTPCStandAlone = fCutRequireTPCStandAlone;
519 target.fCutRequireITSRefit = fCutRequireITSRefit;
520 target.fCutRequireITSPid = fCutRequireITSPid;
521 target.fCutRequireITSStandAlone = fCutRequireITSStandAlone;
522 target.fCutRequireITSpureSA = fCutRequireITSpureSA;
524 target.fCutNsigmaToVertex = fCutNsigmaToVertex;
525 target.fCutSigmaToVertexRequired = fCutSigmaToVertexRequired;
526 target.fCutMaxDCAToVertexXY = fCutMaxDCAToVertexXY;
527 target.fCutMaxDCAToVertexZ = fCutMaxDCAToVertexZ;
528 target.fCutDCAToVertex2D = fCutDCAToVertex2D;
529 target.fCutMinDCAToVertexXY = fCutMinDCAToVertexXY;
530 target.fCutMinDCAToVertexZ = fCutMinDCAToVertexZ;
532 target.fCutMaxDCAToVertexXYPtDep = fCutMaxDCAToVertexXYPtDep;
533 target.SetMaxDCAToVertexXYPtDep(fCutMaxDCAToVertexXYPtDep.Data());
535 target.fCutMaxDCAToVertexZPtDep = fCutMaxDCAToVertexZPtDep;
536 target.SetMaxDCAToVertexZPtDep(fCutMaxDCAToVertexZPtDep.Data());
538 target.fCutMinDCAToVertexXYPtDep = fCutMinDCAToVertexXYPtDep;
539 target.SetMinDCAToVertexXYPtDep(fCutMinDCAToVertexXYPtDep.Data());
541 target.fCutMinDCAToVertexZPtDep = fCutMinDCAToVertexZPtDep;
542 target.SetMinDCAToVertexZPtDep(fCutMinDCAToVertexZPtDep.Data());
544 target.fPMin = fPMin;
545 target.fPMax = fPMax;
546 target.fPtMin = fPtMin;
547 target.fPtMax = fPtMax;
548 target.fPxMin = fPxMin;
549 target.fPxMax = fPxMax;
550 target.fPyMin = fPyMin;
551 target.fPyMax = fPyMax;
552 target.fPzMin = fPzMin;
553 target.fPzMax = fPzMax;
554 target.fEtaMin = fEtaMin;
555 target.fEtaMax = fEtaMax;
556 target.fRapMin = fRapMin;
557 target.fRapMax = fRapMax;
559 target.fHistogramsOn = fHistogramsOn;
561 for (Int_t i=0; i<2; ++i)
563 if (fhNClustersITS[i]) target.fhNClustersITS[i] = (TH1F*) fhNClustersITS[i]->Clone();
564 if (fhNClustersTPC[i]) target.fhNClustersTPC[i] = (TH1F*) fhNClustersTPC[i]->Clone();
565 if (fhNSharedClustersTPC[i]) target.fhNSharedClustersTPC[i] = (TH1F*) fhNSharedClustersTPC[i]->Clone();
566 if (fhNCrossedRowsTPC[i]) target.fhNCrossedRowsTPC[i] = (TH1F*) fhNCrossedRowsTPC[i]->Clone();
567 if (fhRatioCrossedRowsOverFindableClustersTPC[i]) target.fhRatioCrossedRowsOverFindableClustersTPC[i] = (TH1F*) fhRatioCrossedRowsOverFindableClustersTPC[i]->Clone();
569 if (fhChi2PerClusterITS[i]) target.fhChi2PerClusterITS[i] = (TH1F*) fhChi2PerClusterITS[i]->Clone();
570 if (fhChi2PerClusterTPC[i]) target.fhChi2PerClusterTPC[i] = (TH1F*) fhChi2PerClusterTPC[i]->Clone();
571 if (fhChi2TPCConstrainedVsGlobal[i]) target.fhChi2TPCConstrainedVsGlobal[i] = (TH1F*) fhChi2TPCConstrainedVsGlobal[i]->Clone();
572 if (fhNClustersForITSPID[i]) target.fhNClustersForITSPID[i] = (TH1F*) fhNClustersForITSPID[i]->Clone();
573 if (fhNMissingITSPoints[i]) target.fhNMissingITSPoints[i] = (TH1F*) fhNMissingITSPoints[i]->Clone();
575 if (fhC11[i]) target.fhC11[i] = (TH1F*) fhC11[i]->Clone();
576 if (fhC22[i]) target.fhC22[i] = (TH1F*) fhC22[i]->Clone();
577 if (fhC33[i]) target.fhC33[i] = (TH1F*) fhC33[i]->Clone();
578 if (fhC44[i]) target.fhC44[i] = (TH1F*) fhC44[i]->Clone();
579 if (fhC55[i]) target.fhC55[i] = (TH1F*) fhC55[i]->Clone();
581 if (fhRel1PtUncertainty[i]) target.fhRel1PtUncertainty[i] = (TH1F*) fhRel1PtUncertainty[i]->Clone();
583 if (fhDXY[i]) target.fhDXY[i] = (TH1F*) fhDXY[i]->Clone();
584 if (fhDZ[i]) target.fhDZ[i] = (TH1F*) fhDZ[i]->Clone();
585 if (fhDXYDZ[i]) target.fhDXYDZ[i] = (TH1F*) fhDXYDZ[i]->Clone();
586 if (fhDXYvsDZ[i]) target.fhDXYvsDZ[i] = (TH2F*) fhDXYvsDZ[i]->Clone();
588 if (fhDXYNormalized[i]) target.fhDXYNormalized[i] = (TH1F*) fhDXYNormalized[i]->Clone();
589 if (fhDZNormalized[i]) target.fhDZNormalized[i] = (TH1F*) fhDZNormalized[i]->Clone();
590 if (fhDXYvsDZNormalized[i]) target.fhDXYvsDZNormalized[i] = (TH2F*) fhDXYvsDZNormalized[i]->Clone();
591 if (fhNSigmaToVertex[i]) target.fhNSigmaToVertex[i] = (TH1F*) fhNSigmaToVertex[i]->Clone();
593 if (fhPt[i]) target.fhPt[i] = (TH1F*) fhPt[i]->Clone();
594 if (fhEta[i]) target.fhEta[i] = (TH1F*) fhEta[i]->Clone();
596 if (ffDTheoretical) target.ffDTheoretical = (TF1*) ffDTheoretical->Clone();
598 if (fhCutStatistics) target.fhCutStatistics = (TH1F*) fhCutStatistics->Clone();
599 if (fhCutCorrelation) target.fhCutCorrelation = (TH2F*) fhCutCorrelation->Clone();
604 //_____________________________________________________________________________
605 Long64_t AliESDtrackCuts::Merge(TCollection* list) {
606 // Merge a list of AliESDtrackCuts objects with this (needed for PROOF)
607 // Returns the number of merged objects (including this)
614 TIterator* iter = list->MakeIterator();
617 // collection of measured and generated histograms
619 while ((obj = iter->Next())) {
621 AliESDtrackCuts* entry = dynamic_cast<AliESDtrackCuts*>(obj);
625 if (!entry->fHistogramsOn)
628 for (Int_t i=0; i<2; i++) {
630 fhNClustersITS[i] ->Add(entry->fhNClustersITS[i] );
631 fhNClustersTPC[i] ->Add(entry->fhNClustersTPC[i] );
632 if (fhNSharedClustersTPC[i])
633 fhNSharedClustersTPC[i] ->Add(entry->fhNSharedClustersTPC[i] );
634 if (fhNCrossedRowsTPC[i])
635 fhNCrossedRowsTPC[i] ->Add(entry->fhNCrossedRowsTPC[i] );
636 if (fhRatioCrossedRowsOverFindableClustersTPC[i])
637 fhRatioCrossedRowsOverFindableClustersTPC[i] ->Add(entry->fhRatioCrossedRowsOverFindableClustersTPC[i] );
639 fhChi2PerClusterITS[i] ->Add(entry->fhChi2PerClusterITS[i]);
640 fhChi2PerClusterTPC[i] ->Add(entry->fhChi2PerClusterTPC[i]);
641 if (fhChi2TPCConstrainedVsGlobal[i])
642 fhChi2TPCConstrainedVsGlobal[i]->Add(entry->fhChi2TPCConstrainedVsGlobal[i]);
643 if (fhNClustersForITSPID[i])
644 fhNClustersForITSPID[i]->Add(entry->fhNClustersForITSPID[i]);
645 if (fhNMissingITSPoints[i])
646 fhNMissingITSPoints[i] ->Add(entry->fhNMissingITSPoints[i]);
648 fhC11[i] ->Add(entry->fhC11[i] );
649 fhC22[i] ->Add(entry->fhC22[i] );
650 fhC33[i] ->Add(entry->fhC33[i] );
651 fhC44[i] ->Add(entry->fhC44[i] );
652 fhC55[i] ->Add(entry->fhC55[i] );
654 fhRel1PtUncertainty[i] ->Add(entry->fhRel1PtUncertainty[i]);
656 fhDXY[i] ->Add(entry->fhDXY[i] );
657 fhDZ[i] ->Add(entry->fhDZ[i] );
658 fhDXYDZ[i] ->Add(entry->fhDXYDZ[i] );
659 fhDXYvsDZ[i] ->Add(entry->fhDXYvsDZ[i] );
661 fhDXYNormalized[i] ->Add(entry->fhDXYNormalized[i] );
662 fhDZNormalized[i] ->Add(entry->fhDZNormalized[i] );
663 fhDXYvsDZNormalized[i] ->Add(entry->fhDXYvsDZNormalized[i]);
664 fhNSigmaToVertex[i] ->Add(entry->fhNSigmaToVertex[i]);
666 fhPt[i] ->Add(entry->fhPt[i]);
667 fhEta[i] ->Add(entry->fhEta[i]);
670 fhCutStatistics ->Add(entry->fhCutStatistics);
671 fhCutCorrelation ->Add(entry->fhCutCorrelation);
678 void AliESDtrackCuts::SetMinNClustersTPCPtDep(TFormula *f1, Float_t ptmax)
681 // Sets the pT dependent NClustersTPC cut
685 delete f1CutMinNClustersTPCPtDep;
686 f1CutMinNClustersTPCPtDep = (TFormula*)f1->Clone("f1CutMinNClustersTPCPtDep");
688 fCutMaxPtDepNClustersTPC=ptmax;
691 //____________________________________________________________________
692 AliESDtrackCuts* AliESDtrackCuts::GetStandardTPCOnlyTrackCuts()
694 // creates an AliESDtrackCuts object and fills it with standard (pre data-taking) values for TPC-only cuts
696 AliInfoClass("Creating track cuts for TPC-only.");
698 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
700 esdTrackCuts->SetMinNClustersTPC(50);
701 esdTrackCuts->SetMaxChi2PerClusterTPC(4);
702 esdTrackCuts->SetAcceptKinkDaughters(kFALSE);
704 esdTrackCuts->SetMaxDCAToVertexZ(3.2);
705 esdTrackCuts->SetMaxDCAToVertexXY(2.4);
706 esdTrackCuts->SetDCAToVertex2D(kTRUE);
711 //____________________________________________________________________
712 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSTPCTrackCuts2009(Bool_t selPrimaries)
714 // creates an AliESDtrackCuts object and fills it with standard values for ITS-TPC cuts for pp 2009 data
716 AliInfoClass("Creating track cuts for ITS+TPC (2009 definition).");
718 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
721 esdTrackCuts->SetRequireTPCStandAlone(kTRUE); // to get chi2 and ncls of kTPCin
722 esdTrackCuts->SetMinNClustersTPC(70);
723 esdTrackCuts->SetMaxChi2PerClusterTPC(4);
724 esdTrackCuts->SetAcceptKinkDaughters(kFALSE);
725 esdTrackCuts->SetRequireTPCRefit(kTRUE);
727 esdTrackCuts->SetRequireITSRefit(kTRUE);
728 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
729 AliESDtrackCuts::kAny);
731 // 7*(0.0050+0.0060/pt^0.9)
732 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0350+0.0420/pt^0.9");
734 esdTrackCuts->SetMaxDCAToVertexZ(1.e6);
735 esdTrackCuts->SetDCAToVertex2D(kFALSE);
736 esdTrackCuts->SetRequireSigmaToVertex(kFALSE);
737 //esdTrackCuts->SetEtaRange(-0.8,+0.8);
739 esdTrackCuts->SetMaxChi2PerClusterITS(36);
740 esdTrackCuts->SetMaxChi2TPCConstrainedGlobal(36);
745 //____________________________________________________________________
746 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSTPCTrackCuts2010(Bool_t selPrimaries,Int_t clusterCut)
748 // creates an AliESDtrackCuts object and fills it with standard values for ITS-TPC cuts for pp 2010 data
749 // if clusterCut = 1, the cut on the number of clusters is replaced by
750 // a cut on the number of crossed rows and on the ration crossed
751 // rows/findable clusters
753 AliInfoClass("Creating track cuts for ITS+TPC (2010 definition).");
755 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
758 if(clusterCut == 0) esdTrackCuts->SetMinNClustersTPC(70);
759 else if (clusterCut == 1) {
760 esdTrackCuts->SetMinNCrossedRowsTPC(70);
761 esdTrackCuts->SetMinRatioCrossedRowsOverFindableClustersTPC(0.8);
764 AliWarningClass(Form("Wrong value of the clusterCut parameter (%d), using cut on Nclusters",clusterCut));
765 esdTrackCuts->SetMinNClustersTPC(70);
767 esdTrackCuts->SetMaxChi2PerClusterTPC(4);
768 esdTrackCuts->SetAcceptKinkDaughters(kFALSE);
769 esdTrackCuts->SetRequireTPCRefit(kTRUE);
771 esdTrackCuts->SetRequireITSRefit(kTRUE);
772 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
773 AliESDtrackCuts::kAny);
775 // 7*(0.0026+0.0050/pt^1.01)
776 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0182+0.0350/pt^1.01");
778 esdTrackCuts->SetMaxDCAToVertexZ(2);
779 esdTrackCuts->SetDCAToVertex2D(kFALSE);
780 esdTrackCuts->SetRequireSigmaToVertex(kFALSE);
782 esdTrackCuts->SetMaxChi2PerClusterITS(36);
783 esdTrackCuts->SetMaxChi2TPCConstrainedGlobal(36);
788 //____________________________________________________________________
789 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSPureSATrackCuts2009(Bool_t selPrimaries, Bool_t useForPid)
791 // creates an AliESDtrackCuts object and fills it with standard values for ITS pure SA tracks
793 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
794 esdTrackCuts->SetRequireITSPureStandAlone(kTRUE);
795 esdTrackCuts->SetRequireITSRefit(kTRUE);
796 esdTrackCuts->SetMinNClustersITS(4);
797 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
798 AliESDtrackCuts::kAny);
799 esdTrackCuts->SetMaxChi2PerClusterITS(1.);
802 // 7*(0.0085+0.0026/pt^1.55)
803 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0595+0.0182/pt^1.55");
806 esdTrackCuts->SetRequireITSPid(kTRUE);
811 //____________________________________________________________________
812 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSPureSATrackCuts2010(Bool_t selPrimaries, Bool_t useForPid)
814 // creates an AliESDtrackCuts object and fills it with standard values for ITS pure SA tracks - pp 2010
816 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
817 esdTrackCuts->SetRequireITSPureStandAlone(kTRUE);
818 esdTrackCuts->SetRequireITSRefit(kTRUE);
819 esdTrackCuts->SetMinNClustersITS(4);
820 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
821 AliESDtrackCuts::kAny);
822 esdTrackCuts->SetMaxChi2PerClusterITS(2.5);
825 // 7*(0.0033+0.0045/pt^1.3)
826 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0231+0.0315/pt^1.3");
829 esdTrackCuts->SetRequireITSPid(kTRUE);
834 //____________________________________________________________________
835 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSSATrackCuts2009(Bool_t selPrimaries, Bool_t useForPid)
837 // creates an AliESDtrackCuts object and fills it with standard values for ITS pure SA tracks
839 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
840 esdTrackCuts->SetRequireITSStandAlone(kTRUE);
841 esdTrackCuts->SetRequireITSPureStandAlone(kFALSE);
842 esdTrackCuts->SetRequireITSRefit(kTRUE);
843 esdTrackCuts->SetMinNClustersITS(4);
844 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
845 AliESDtrackCuts::kAny);
846 esdTrackCuts->SetMaxChi2PerClusterITS(1.);
849 // 7*(0.0085+0.0026/pt^1.55)
850 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0595+0.0182/pt^1.55");
853 esdTrackCuts->SetRequireITSPid(kTRUE);
858 //____________________________________________________________________
859 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSSATrackCuts2010(Bool_t selPrimaries, Bool_t useForPid)
861 // creates an AliESDtrackCuts object and fills it with standard values for ITS pure SA tracks --pp 2010
863 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
864 esdTrackCuts->SetRequireITSStandAlone(kTRUE);
865 esdTrackCuts->SetRequireITSPureStandAlone(kFALSE);
866 esdTrackCuts->SetRequireITSRefit(kTRUE);
867 esdTrackCuts->SetMinNClustersITS(4);
868 esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
869 AliESDtrackCuts::kAny);
870 esdTrackCuts->SetMaxChi2PerClusterITS(2.5);
873 // 7*(0.0033+0.0045/pt^1.3)
874 esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0231+0.0315/pt^1.3");
877 esdTrackCuts->SetRequireITSPid(kTRUE);
882 //____________________________________________________________________
883 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSSATrackCutsPbPb2010(Bool_t selPrimaries, Bool_t useForPid)
885 // creates an AliESDtrackCuts object and fills it with standard values for ITS pure SA tracks -- PbPb 2010
887 AliESDtrackCuts* esdTrackCuts = GetStandardITSSATrackCuts2010(selPrimaries, useForPid);
888 esdTrackCuts->SetMaxNOfMissingITSPoints(1);
892 //____________________________________________________________________
894 AliESDtrackCuts* AliESDtrackCuts::GetStandardV0DaughterCuts()
896 // creates a AliESDtrackCuts object and fills it with standard cuts for V0 daughters
897 AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
898 esdTrackCuts->SetRequireTPCRefit(kTRUE);
899 esdTrackCuts->SetMinNClustersTPC(70);
900 esdTrackCuts->SetAcceptKinkDaughters(kFALSE);
904 //____________________________________________________________________
905 Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, Bool_t tpcOnly)
907 // Gets reference multiplicity following the standard cuts and a defined fiducial volume
908 // tpcOnly = kTRUE -> consider TPC-only tracks
909 // = kFALSE -> consider global tracks
911 // DEPRECATED Use GetReferenceMultiplicity with the enum as second argument instead
915 AliErrorClass("Not implemented for global tracks!");
919 static AliESDtrackCuts* esdTrackCuts = 0;
922 esdTrackCuts = GetStandardTPCOnlyTrackCuts();
923 esdTrackCuts->SetEtaRange(-0.8, 0.8);
924 esdTrackCuts->SetPtRange(0.15);
927 Int_t nTracks = esdTrackCuts->CountAcceptedTracks(esd);
932 //____________________________________________________________________
933 Float_t AliESDtrackCuts::GetSigmaToVertex(const AliESDtrack* const esdTrack)
935 // Calculates the number of sigma to the vertex.
940 esdTrack->GetImpactParameters(b,bCov);
942 if (bCov[0]<=0 || bCov[2]<=0) {
943 AliDebugClass(1, "Estimated b resolution lower or equal zero!");
944 bCov[0]=0; bCov[2]=0;
946 bRes[0] = TMath::Sqrt(bCov[0]);
947 bRes[1] = TMath::Sqrt(bCov[2]);
949 // -----------------------------------
950 // How to get to a n-sigma cut?
952 // The accumulated statistics from 0 to d is
954 // -> Erf(d/Sqrt(2)) for a 1-dim gauss (d = n_sigma)
955 // -> 1 - Exp(-d**2) for a 2-dim gauss (d*d = dx*dx + dy*dy != n_sigma)
957 // It means that for a 2-dim gauss: n_sigma(d) = Sqrt(2)*ErfInv(1 - Exp((-d**2)/2)
958 // Can this be expressed in a different way?
960 if (bRes[0] == 0 || bRes[1] ==0)
963 Float_t d = TMath::Sqrt(TMath::Power(b[0]/bRes[0],2) + TMath::Power(b[1]/bRes[1],2));
965 // work around precision problem
966 // if d is too big, TMath::Exp(...) gets 0, and TMath::ErfInverse(1) that should be infinite, gets 0 :(
967 // 1e-15 corresponds to nsigma ~ 7.7
968 if (TMath::Exp(-d * d / 2) < 1e-15)
971 Float_t nSigma = TMath::ErfInverse(1 - TMath::Exp(-d * d / 2)) * TMath::Sqrt(2);
975 void AliESDtrackCuts::EnableNeededBranches(TTree* tree)
977 // enables the branches needed by AcceptTrack, for a list see comment of AcceptTrack
979 tree->SetBranchStatus("fTracks.fFlags", 1);
980 tree->SetBranchStatus("fTracks.fITSncls", 1);
981 tree->SetBranchStatus("fTracks.fTPCncls", 1);
982 tree->SetBranchStatus("fTracks.fITSchi2", 1);
983 tree->SetBranchStatus("fTracks.fTPCchi2", 1);
984 tree->SetBranchStatus("fTracks.fC*", 1);
985 tree->SetBranchStatus("fTracks.fD", 1);
986 tree->SetBranchStatus("fTracks.fZ", 1);
987 tree->SetBranchStatus("fTracks.fCdd", 1);
988 tree->SetBranchStatus("fTracks.fCdz", 1);
989 tree->SetBranchStatus("fTracks.fCzz", 1);
990 tree->SetBranchStatus("fTracks.fP*", 1);
991 tree->SetBranchStatus("fTracks.fR*", 1);
992 tree->SetBranchStatus("fTracks.fKinkIndexes*", 1);
995 //____________________________________________________________________
996 Bool_t AliESDtrackCuts::AcceptTrack(const AliESDtrack* esdTrack, const AliESDEvent* esdEvent)
999 // figure out if the tracks survives all the track cuts defined
1001 // the different quality parameter and kinematic values are first
1002 // retrieved from the track. then it is found out what cuts the
1003 // track did not survive and finally the cuts are imposed.
1005 // this function needs the following branches:
1011 // fTracks.fC //GetExternalCovariance
1012 // fTracks.fD //GetImpactParameters
1013 // fTracks.fZ //GetImpactParameters
1014 // fTracks.fCdd //GetImpactParameters
1015 // fTracks.fCdz //GetImpactParameters
1016 // fTracks.fCzz //GetImpactParameters
1017 // fTracks.fP //GetPxPyPz
1018 // fTracks.fR //GetMass
1019 // fTracks.fP //GetMass
1020 // fTracks.fKinkIndexes
1022 // esdEvent is only required for the MaxChi2TPCConstrainedVsGlobal
1024 UInt_t status = esdTrack->GetStatus();
1026 // getting quality parameters from the ESD track
1027 Int_t nClustersITS = esdTrack->GetITSclusters(0);
1028 Int_t nClustersTPC = -1;
1029 if(fCutRequireTPCStandAlone) {
1030 nClustersTPC = esdTrack->GetTPCNclsIter1();
1033 nClustersTPC = esdTrack->GetTPCclusters(0);
1036 //Pt dependent NClusters Cut
1037 if(f1CutMinNClustersTPCPtDep) {
1038 if(esdTrack->Pt()<fCutMaxPtDepNClustersTPC)
1039 fCutMinNClusterTPC = f1CutMinNClustersTPCPtDep->Eval(esdTrack->Pt());
1041 fCutMinNClusterTPC = f1CutMinNClustersTPCPtDep->Eval(fCutMaxPtDepNClustersTPC);
1044 Float_t nCrossedRowsTPC = esdTrack->GetTPCCrossedRows();
1045 Float_t ratioCrossedRowsOverFindableClustersTPC = 1.0;
1046 if (esdTrack->GetTPCNclsF()>0) {
1047 ratioCrossedRowsOverFindableClustersTPC = nCrossedRowsTPC / esdTrack->GetTPCNclsF();
1050 Int_t nClustersTPCShared = esdTrack->GetTPCnclsS();
1051 Float_t fracClustersTPCShared = -1.;
1053 Float_t chi2PerClusterITS = -1;
1054 Float_t chi2PerClusterTPC = -1;
1055 if (nClustersITS!=0)
1056 chi2PerClusterITS = esdTrack->GetITSchi2()/Float_t(nClustersITS);
1057 if (nClustersTPC!=0) {
1058 if(fCutRequireTPCStandAlone) {
1059 chi2PerClusterTPC = esdTrack->GetTPCchi2Iter1()/Float_t(nClustersTPC);
1061 chi2PerClusterTPC = esdTrack->GetTPCchi2()/Float_t(nClustersTPC);
1063 fracClustersTPCShared = Float_t(nClustersTPCShared)/Float_t(nClustersTPC);
1066 Double_t extCov[15];
1067 esdTrack->GetExternalCovariance(extCov);
1071 esdTrack->GetImpactParameters(b,bCov);
1072 if (bCov[0]<=0 || bCov[2]<=0) {
1073 AliDebug(1, "Estimated b resolution lower or equal zero!");
1074 bCov[0]=0; bCov[2]=0;
1078 // set pt-dependent DCA cuts, if requested
1079 SetPtDepDCACuts(esdTrack->Pt());
1082 Float_t dcaToVertexXY = b[0];
1083 Float_t dcaToVertexZ = b[1];
1085 Float_t dcaToVertex = -1;
1087 if (fCutDCAToVertex2D)
1089 dcaToVertex = TMath::Sqrt(dcaToVertexXY*dcaToVertexXY/fCutMaxDCAToVertexXY/fCutMaxDCAToVertexXY + dcaToVertexZ*dcaToVertexZ/fCutMaxDCAToVertexZ/fCutMaxDCAToVertexZ);
1092 dcaToVertex = TMath::Sqrt(dcaToVertexXY*dcaToVertexXY + dcaToVertexZ*dcaToVertexZ);
1094 // getting the kinematic variables of the track
1095 // (assuming the mass is known)
1097 esdTrack->GetPxPyPz(p);
1099 Float_t momentum = TMath::Sqrt(TMath::Power(p[0],2) + TMath::Power(p[1],2) + TMath::Power(p[2],2));
1100 Float_t pt = TMath::Sqrt(TMath::Power(p[0],2) + TMath::Power(p[1],2));
1101 Float_t energy = TMath::Sqrt(TMath::Power(esdTrack->GetMass(),2) + TMath::Power(momentum,2));
1103 //y-eta related calculations
1104 Float_t eta = -100.;
1106 if((momentum != TMath::Abs(p[2]))&&(momentum != 0))
1107 eta = 0.5*TMath::Log((momentum + p[2])/(momentum - p[2]));
1108 if((energy != TMath::Abs(p[2]))&&(momentum != 0))
1109 y = 0.5*TMath::Log((energy + p[2])/(energy - p[2]));
1113 AliWarning(Form("GetSigma1Pt2() returns negative value for external covariance matrix element fC[14]: %f. Corrupted track information, track will not be accepted!", extCov[14]));
1116 Float_t relUncertainty1Pt = TMath::Sqrt(extCov[14])*pt;
1118 //########################################################################
1121 Bool_t cuts[kNCuts];
1122 for (Int_t i=0; i<kNCuts; i++) cuts[i]=kFALSE;
1124 // track quality cuts
1125 if (fCutRequireTPCRefit && (status&AliESDtrack::kTPCrefit)==0)
1127 if (fCutRequireTPCStandAlone && (status&AliESDtrack::kTPCin)==0)
1129 if (fCutRequireITSRefit && (status&AliESDtrack::kITSrefit)==0)
1131 if (nClustersTPC<fCutMinNClusterTPC)
1133 if (nClustersITS<fCutMinNClusterITS)
1135 if (chi2PerClusterTPC>fCutMaxChi2PerClusterTPC)
1137 if (chi2PerClusterITS>fCutMaxChi2PerClusterITS)
1139 if (extCov[0] > fCutMaxC11)
1141 if (extCov[2] > fCutMaxC22)
1143 if (extCov[5] > fCutMaxC33)
1145 if (extCov[9] > fCutMaxC44)
1147 if (extCov[14] > fCutMaxC55)
1150 // cut 12 and 13 see below
1152 if (!fCutAcceptKinkDaughters && esdTrack->GetKinkIndex(0)>0)
1154 // track kinematics cut
1155 if((momentum < fPMin) || (momentum > fPMax))
1157 if((pt < fPtMin) || (pt > fPtMax))
1159 if((p[0] < fPxMin) || (p[0] > fPxMax))
1161 if((p[1] < fPyMin) || (p[1] > fPyMax))
1163 if((p[2] < fPzMin) || (p[2] > fPzMax))
1165 if((eta < fEtaMin) || (eta > fEtaMax))
1167 if((y < fRapMin) || (y > fRapMax))
1169 if (fCutDCAToVertex2D && dcaToVertex > 1)
1171 if (!fCutDCAToVertex2D && TMath::Abs(dcaToVertexXY) > fCutMaxDCAToVertexXY)
1173 if (!fCutDCAToVertex2D && TMath::Abs(dcaToVertexZ) > fCutMaxDCAToVertexZ)
1175 if (fCutDCAToVertex2D && fCutMinDCAToVertexXY > 0 && fCutMinDCAToVertexZ > 0 && dcaToVertexXY*dcaToVertexXY/fCutMinDCAToVertexXY/fCutMinDCAToVertexXY + dcaToVertexZ*dcaToVertexZ/fCutMinDCAToVertexZ/fCutMinDCAToVertexZ < 1)
1177 if (!fCutDCAToVertex2D && TMath::Abs(dcaToVertexXY) < fCutMinDCAToVertexXY)
1179 if (!fCutDCAToVertex2D && TMath::Abs(dcaToVertexZ) < fCutMinDCAToVertexZ)
1182 for (Int_t i = 0; i < 3; i++)
1183 cuts[28+i] = !CheckITSClusterRequirement(fCutClusterRequirementITS[i], esdTrack->HasPointOnITSLayer(i*2), esdTrack->HasPointOnITSLayer(i*2+1));
1185 if(fCutRequireITSStandAlone || fCutRequireITSpureSA){
1186 if ((status & AliESDtrack::kITSin) == 0 || (status & AliESDtrack::kTPCin)){
1190 // ITS standalone tracks
1191 if(fCutRequireITSStandAlone && !fCutRequireITSpureSA){
1192 if(status & AliESDtrack::kITSpureSA) cuts[31] = kTRUE;
1193 }else if(fCutRequireITSpureSA){
1194 if(!(status & AliESDtrack::kITSpureSA)) cuts[31] = kTRUE;
1199 if (relUncertainty1Pt > fCutMaxRel1PtUncertainty)
1202 if (!fCutAcceptSharedTPCClusters && nClustersTPCShared!=0)
1205 if (fracClustersTPCShared > fCutMaxFractionSharedTPCClusters)
1208 Int_t nITSPointsForPid=0;
1209 UChar_t clumap=esdTrack->GetITSClusterMap();
1210 for(Int_t i=2; i<6; i++){
1211 if(clumap&(1<<i)) ++nITSPointsForPid;
1213 if(fCutRequireITSPid && nITSPointsForPid<3) cuts[35] = kTRUE;
1216 if (nCrossedRowsTPC<fCutMinNCrossedRowsTPC)
1218 if (ratioCrossedRowsOverFindableClustersTPC<fCutMinRatioCrossedRowsOverFindableClustersTPC)
1221 Int_t nMissITSpts=0;
1222 Int_t idet,statusLay;
1224 for(Int_t iLay=0; iLay<6; iLay++){
1225 Bool_t retc=esdTrack->GetITSModuleIndexInfo(iLay,idet,statusLay,xloc,zloc);
1226 if(retc && statusLay==5) ++nMissITSpts;
1228 if(nMissITSpts>fCutMaxMissingITSPoints) cuts[38] = kTRUE;
1231 for (Int_t i=0; i<kNCuts; i++)
1232 if (cuts[i]) {cut = kTRUE;}
1234 // for performance evaluate the CPU intensive cuts only when the others have passed, and when they are requested
1235 Double_t chi2TPCConstrainedVsGlobal = -2;
1236 Float_t nSigmaToVertex = -2;
1239 // getting the track to vertex parameters
1240 if (fCutSigmaToVertexRequired)
1242 nSigmaToVertex = GetSigmaToVertex(esdTrack);
1243 if (nSigmaToVertex > fCutNsigmaToVertex && fCutSigmaToVertexRequired)
1248 // if n sigma could not be calculated
1249 if (nSigmaToVertex<0 && fCutSigmaToVertexRequired)
1256 // max chi2 TPC constrained vs global track only if track passed the other cut
1257 if (fCutMaxChi2TPCConstrainedVsGlobal < 1e9)
1260 AliFatal("fCutMaxChi2TPCConstrainedVsGlobal set but ESD event not provided.");
1263 const AliESDVertex* vertex = 0;
1264 if (fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexTracks)
1265 vertex = esdEvent->GetPrimaryVertexTracks();
1267 if ((!vertex || !vertex->GetStatus()) && fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexSPD)
1268 vertex = esdEvent->GetPrimaryVertexSPD();
1270 if ((!vertex || !vertex->GetStatus()) && fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexTPC)
1271 vertex = esdEvent->GetPrimaryVertexTPC();
1273 if (vertex->GetStatus())
1274 chi2TPCConstrainedVsGlobal = esdTrack->GetChi2TPCConstrainedVsGlobal(vertex);
1276 if (chi2TPCConstrainedVsGlobal < 0 || chi2TPCConstrainedVsGlobal > fCutMaxChi2TPCConstrainedVsGlobal)
1284 //########################################################################
1285 // filling histograms
1286 if (fHistogramsOn) {
1287 fhCutStatistics->Fill(fhCutStatistics->GetBinCenter(fhCutStatistics->GetXaxis()->FindBin("n tracks")));
1289 fhCutStatistics->Fill(fhCutStatistics->GetBinCenter(fhCutStatistics->GetXaxis()->FindBin("n cut tracks")));
1291 for (Int_t i=0; i<kNCuts; i++) {
1292 if (fhCutStatistics->GetXaxis()->FindBin(fgkCutNames[i]) < 1)
1293 AliFatal(Form("Inconsistency! Cut %d with name %s not found", i, fgkCutNames[i]));
1296 fhCutStatistics->Fill(fhCutStatistics->GetBinCenter(fhCutStatistics->GetXaxis()->FindBin(fgkCutNames[i])));
1298 for (Int_t j=i; j<kNCuts; j++) {
1299 if (cuts[i] && cuts[j]) {
1300 Float_t xC = fhCutCorrelation->GetXaxis()->GetBinCenter(fhCutCorrelation->GetXaxis()->FindBin(fgkCutNames[i]));
1301 Float_t yC = fhCutCorrelation->GetYaxis()->GetBinCenter(fhCutCorrelation->GetYaxis()->FindBin(fgkCutNames[j]));
1302 fhCutCorrelation->Fill(xC, yC);
1308 // now we loop over the filling of the histograms twice: once "before" the cut, once "after"
1309 // the code is not in a function due to too many local variables that would need to be passed
1311 for (Int_t id = 0; id < 2; id++)
1313 // id = 0 --> before cut
1314 // id = 1 --> after cut
1318 fhNClustersITS[id]->Fill(nClustersITS);
1319 fhNClustersTPC[id]->Fill(nClustersTPC);
1320 fhNSharedClustersTPC[id]->Fill(nClustersTPCShared);
1321 fhNCrossedRowsTPC[id]->Fill(nCrossedRowsTPC);
1322 fhRatioCrossedRowsOverFindableClustersTPC[id]->Fill(ratioCrossedRowsOverFindableClustersTPC);
1323 fhChi2PerClusterITS[id]->Fill(chi2PerClusterITS);
1324 fhChi2PerClusterTPC[id]->Fill(chi2PerClusterTPC);
1325 fhChi2TPCConstrainedVsGlobal[id]->Fill(chi2TPCConstrainedVsGlobal);
1326 fhNClustersForITSPID[id]->Fill(nITSPointsForPid);
1327 fhNMissingITSPoints[id]->Fill(nMissITSpts);
1329 fhC11[id]->Fill(extCov[0]);
1330 fhC22[id]->Fill(extCov[2]);
1331 fhC33[id]->Fill(extCov[5]);
1332 fhC44[id]->Fill(extCov[9]);
1333 fhC55[id]->Fill(extCov[14]);
1335 fhRel1PtUncertainty[id]->Fill(relUncertainty1Pt);
1338 fhEta[id]->Fill(eta);
1341 bRes[0] = TMath::Sqrt(bCov[0]);
1342 bRes[1] = TMath::Sqrt(bCov[2]);
1344 fhDZ[id]->Fill(b[1]);
1345 fhDXY[id]->Fill(b[0]);
1346 fhDXYDZ[id]->Fill(dcaToVertex);
1347 fhDXYvsDZ[id]->Fill(b[1],b[0]);
1349 if (bRes[0]!=0 && bRes[1]!=0) {
1350 fhDZNormalized[id]->Fill(b[1]/bRes[1]);
1351 fhDXYNormalized[id]->Fill(b[0]/bRes[0]);
1352 fhDXYvsDZNormalized[id]->Fill(b[1]/bRes[1], b[0]/bRes[0]);
1353 fhNSigmaToVertex[id]->Fill(nSigmaToVertex);
1365 //____________________________________________________________________
1366 Bool_t AliESDtrackCuts::CheckITSClusterRequirement(ITSClusterRequirement req, Bool_t clusterL1, Bool_t clusterL2)
1368 // checks if the cluster requirement is fullfilled (in this case: return kTRUE)
1372 case kOff: return kTRUE;
1373 case kNone: return !clusterL1 && !clusterL2;
1374 case kAny: return clusterL1 || clusterL2;
1375 case kFirst: return clusterL1;
1376 case kOnlyFirst: return clusterL1 && !clusterL2;
1377 case kSecond: return clusterL2;
1378 case kOnlySecond: return clusterL2 && !clusterL1;
1379 case kBoth: return clusterL1 && clusterL2;
1385 //____________________________________________________________________
1386 AliESDtrack* AliESDtrackCuts::GetTPCOnlyTrack(const AliESDEvent* esd, Int_t iTrack)
1388 // Utility function to create a TPC only track from the given esd track
1390 // IMPORTANT: The track has to be deleted by the user
1392 // NB. most of the functionality to get a TPC only track from an ESD track is in AliESDtrack, where it should be
1393 // there are only missing propagations here that are needed for old data
1394 // this function will therefore become obsolete
1396 // adapted from code provided by CKB
1398 if (!esd->GetPrimaryVertexTPC())
1399 return 0; // No TPC vertex no TPC tracks
1401 if(!esd->GetPrimaryVertexTPC()->GetStatus())
1402 return 0; // TPC Vertex is created by default in AliESDEvent, do not use in this case
1404 AliESDtrack* track = esd->GetTrack(iTrack);
1408 AliESDtrack *tpcTrack = new AliESDtrack();
1410 // only true if we have a tpc track
1411 if (!track->FillTPCOnlyTrack(*tpcTrack))
1420 //____________________________________________________________________
1421 TObjArray* AliESDtrackCuts::GetAcceptedTracks(const AliESDEvent* esd, Bool_t bTPC)
1424 // returns an array of all tracks that pass the cuts
1425 // or an array of TPC only tracks (propagated to the TPC vertex during reco)
1426 // tracks that pass the cut
1428 // NOTE: List has to be deleted by the user
1430 TObjArray* acceptedTracks = new TObjArray();
1432 // loop over esd tracks
1433 for (Int_t iTrack = 0; iTrack < esd->GetNumberOfTracks(); iTrack++) {
1435 if(!esd->GetPrimaryVertexTPC())return acceptedTracks; // No TPC vertex no TPC tracks
1436 if(!esd->GetPrimaryVertexTPC()->GetStatus())return acceptedTracks; // No proper TPC vertex, only the default
1438 AliESDtrack *tpcTrack = GetTPCOnlyTrack(esd, iTrack);
1442 if (AcceptTrack(tpcTrack, esd)) {
1443 acceptedTracks->Add(tpcTrack);
1450 AliESDtrack* track = esd->GetTrack(iTrack);
1451 if(AcceptTrack(track, esd))
1452 acceptedTracks->Add(track);
1455 if(bTPC)acceptedTracks->SetOwner(kTRUE);
1456 return acceptedTracks;
1459 //____________________________________________________________________
1460 Int_t AliESDtrackCuts::CountAcceptedTracks(const AliESDEvent* const esd)
1463 // returns an the number of tracks that pass the cuts
1468 // loop over esd tracks
1469 for (Int_t iTrack = 0; iTrack < esd->GetNumberOfTracks(); iTrack++) {
1470 AliESDtrack* track = esd->GetTrack(iTrack);
1471 if (AcceptTrack(track, esd))
1478 //____________________________________________________________________
1479 void AliESDtrackCuts::DefineHistograms(Int_t color) {
1481 // diagnostics histograms are defined
1484 fHistogramsOn=kTRUE;
1486 Bool_t oldStatus = TH1::AddDirectoryStatus();
1487 TH1::AddDirectory(kFALSE);
1489 //###################################################################################
1490 // defining histograms
1492 fhCutStatistics = new TH1F("cut_statistics","cut statistics",kNCuts+4,-0.5,kNCuts+3.5);
1494 fhCutStatistics->GetXaxis()->SetBinLabel(1,"n tracks");
1495 fhCutStatistics->GetXaxis()->SetBinLabel(2,"n cut tracks");
1497 fhCutCorrelation = new TH2F("cut_correlation","cut correlation",kNCuts,-0.5,kNCuts-0.5,kNCuts,-0.5,kNCuts-0.5);;
1499 for (Int_t i=0; i<kNCuts; i++) {
1500 fhCutStatistics->GetXaxis()->SetBinLabel(i+4,fgkCutNames[i]);
1501 fhCutCorrelation->GetXaxis()->SetBinLabel(i+1,fgkCutNames[i]);
1502 fhCutCorrelation->GetYaxis()->SetBinLabel(i+1,fgkCutNames[i]);
1505 fhCutStatistics ->SetLineColor(color);
1506 fhCutCorrelation ->SetLineColor(color);
1507 fhCutStatistics ->SetLineWidth(2);
1508 fhCutCorrelation ->SetLineWidth(2);
1510 for (Int_t i=0; i<2; i++) {
1511 fhNClustersITS[i] = new TH1F("nClustersITS" ,"",8,-0.5,7.5);
1512 fhNClustersTPC[i] = new TH1F("nClustersTPC" ,"",165,-0.5,164.5);
1513 fhNSharedClustersTPC[i] = new TH1F("nSharedClustersTPC" ,"",165,-0.5,164.5);
1514 fhNCrossedRowsTPC[i] = new TH1F("nCrossedRowsTPC" ,"",165,-0.5,164.5);
1515 fhRatioCrossedRowsOverFindableClustersTPC[i] = new TH1F("ratioCrossedRowsOverFindableClustersTPC" ,"",60,0,1.5);
1516 fhChi2PerClusterITS[i] = new TH1F("chi2PerClusterITS","",500,0,10);
1517 fhChi2PerClusterTPC[i] = new TH1F("chi2PerClusterTPC","",500,0,10);
1518 fhChi2TPCConstrainedVsGlobal[i] = new TH1F("chi2TPCConstrainedVsGlobal","",600,-2,50);
1519 fhNClustersForITSPID[i] = new TH1F("nPointsForITSpid","",5,-0.5,4.5);
1520 fhNMissingITSPoints[i] = new TH1F("nMissingITSClusters","",7,-0.5,6.5);
1522 fhC11[i] = new TH1F("covMatrixDiagonal11","",2000,0,20);
1523 fhC22[i] = new TH1F("covMatrixDiagonal22","",2000,0,20);
1524 fhC33[i] = new TH1F("covMatrixDiagonal33","",1000,0,0.1);
1525 fhC44[i] = new TH1F("covMatrixDiagonal44","",1000,0,0.1);
1526 fhC55[i] = new TH1F("covMatrixDiagonal55","",1000,0,5);
1528 fhRel1PtUncertainty[i] = new TH1F("rel1PtUncertainty","",1000,0,5);
1530 fhDXY[i] = new TH1F("dXY" ,"",500,-10,10);
1531 fhDZ[i] = new TH1F("dZ" ,"",500,-10,10);
1532 fhDXYDZ[i] = new TH1F("dXYDZ" ,"",500,0,10);
1533 fhDXYvsDZ[i] = new TH2F("dXYvsDZ","",200,-10,10,200,-10,10);
1535 fhDXYNormalized[i] = new TH1F("dXYNormalized" ,"",500,-10,10);
1536 fhDZNormalized[i] = new TH1F("dZNormalized" ,"",500,-10,10);
1537 fhDXYvsDZNormalized[i] = new TH2F("dXYvsDZNormalized","",200,-10,10,200,-10,10);
1539 fhNSigmaToVertex[i] = new TH1F("nSigmaToVertex","",500,0,10);
1541 fhPt[i] = new TH1F("pt" ,"p_{T} distribution;p_{T} (GeV/c)", 800, 0.0, 10.0);
1542 fhEta[i] = new TH1F("eta" ,"#eta distribution;#eta",40,-2.0,2.0);
1544 fhNClustersITS[i]->SetTitle("n ITS clusters");
1545 fhNClustersTPC[i]->SetTitle("n TPC clusters");
1546 fhNSharedClustersTPC[i]->SetTitle("n TPC shared clusters");
1547 fhChi2PerClusterITS[i]->SetTitle("#Chi^{2} per ITS cluster");
1548 fhChi2PerClusterTPC[i]->SetTitle("#Chi^{2} per TPC cluster");
1549 fhChi2TPCConstrainedVsGlobal[i]->SetTitle("#Chi^{2} TPC constrained track vs global track");
1550 fhNClustersForITSPID[i]->SetTitle("n ITS points for PID");
1551 fhNMissingITSPoints[i]->SetTitle("n ITS layers with missing cluster");
1553 fhC11[i]->SetTitle("cov 11 : #sigma_{y}^{2} [cm^{2}]");
1554 fhC22[i]->SetTitle("cov 22 : #sigma_{z}^{2} [cm^{2}]");
1555 fhC33[i]->SetTitle("cov 33 : #sigma_{sin(#phi)}^{2}");
1556 fhC44[i]->SetTitle("cov 44 : #sigma_{tan(#theta_{dip})}^{2}");
1557 fhC55[i]->SetTitle("cov 55 : #sigma_{1/p_{T}}^{2} [(c/GeV)^2]");
1559 fhRel1PtUncertainty[i]->SetTitle("rel. uncertainty of 1/p_{T}");
1561 fhDXY[i]->SetXTitle("transverse impact parameter (cm)");
1562 fhDZ[i]->SetXTitle("longitudinal impact parameter (cm)");
1563 fhDXYDZ[i]->SetTitle("absolute impact parameter;sqrt(dXY**2 + dZ**2) (cm)");
1564 fhDXYvsDZ[i]->SetXTitle("longitudinal impact parameter (cm)");
1565 fhDXYvsDZ[i]->SetYTitle("transverse impact parameter (cm)");
1567 fhDXYNormalized[i]->SetTitle("normalized trans impact par (n#sigma)");
1568 fhDZNormalized[i]->SetTitle("normalized long impact par (n#sigma)");
1569 fhDXYvsDZNormalized[i]->SetTitle("normalized long impact par (n#sigma)");
1570 fhDXYvsDZNormalized[i]->SetYTitle("normalized trans impact par (n#sigma)");
1571 fhNSigmaToVertex[i]->SetTitle("n #sigma to vertex");
1573 fhNClustersITS[i]->SetLineColor(color); fhNClustersITS[i]->SetLineWidth(2);
1574 fhNClustersTPC[i]->SetLineColor(color); fhNClustersTPC[i]->SetLineWidth(2);
1575 fhNSharedClustersTPC[i]->SetLineColor(color); fhNSharedClustersTPC[i]->SetLineWidth(2);
1576 fhChi2PerClusterITS[i]->SetLineColor(color); fhChi2PerClusterITS[i]->SetLineWidth(2);
1577 fhChi2PerClusterTPC[i]->SetLineColor(color); fhChi2PerClusterTPC[i]->SetLineWidth(2);
1578 fhChi2TPCConstrainedVsGlobal[i]->SetLineColor(color); fhChi2TPCConstrainedVsGlobal[i]->SetLineWidth(2);
1579 fhNClustersForITSPID[i]->SetLineColor(color); fhNClustersForITSPID[i]->SetLineWidth(2);
1580 fhNMissingITSPoints[i]->SetLineColor(color); fhNMissingITSPoints[i]->SetLineWidth(2);
1582 fhC11[i]->SetLineColor(color); fhC11[i]->SetLineWidth(2);
1583 fhC22[i]->SetLineColor(color); fhC22[i]->SetLineWidth(2);
1584 fhC33[i]->SetLineColor(color); fhC33[i]->SetLineWidth(2);
1585 fhC44[i]->SetLineColor(color); fhC44[i]->SetLineWidth(2);
1586 fhC55[i]->SetLineColor(color); fhC55[i]->SetLineWidth(2);
1588 fhRel1PtUncertainty[i]->SetLineColor(color); fhRel1PtUncertainty[i]->SetLineWidth(2);
1590 fhDXY[i]->SetLineColor(color); fhDXY[i]->SetLineWidth(2);
1591 fhDZ[i]->SetLineColor(color); fhDZ[i]->SetLineWidth(2);
1592 fhDXYDZ[i]->SetLineColor(color); fhDXYDZ[i]->SetLineWidth(2);
1594 fhDXYNormalized[i]->SetLineColor(color); fhDXYNormalized[i]->SetLineWidth(2);
1595 fhDZNormalized[i]->SetLineColor(color); fhDZNormalized[i]->SetLineWidth(2);
1596 fhNSigmaToVertex[i]->SetLineColor(color); fhNSigmaToVertex[i]->SetLineWidth(2);
1599 // The number of sigmas to the vertex is per definition gaussian
1600 ffDTheoretical = new TF1("nSigmaToVertexTheoretical","([0]/2.506628274)*exp(-(x**2)/2)",0,50);
1601 ffDTheoretical->SetParameter(0,1);
1603 TH1::AddDirectory(oldStatus);
1606 //____________________________________________________________________
1607 Bool_t AliESDtrackCuts::LoadHistograms(const Char_t* dir)
1610 // loads the histograms from a file
1611 // if dir is empty a directory with the name of this object is taken (like in SaveHistogram)
1617 if (!gDirectory->cd(dir))
1620 ffDTheoretical = dynamic_cast<TF1*> (gDirectory->Get("nSigmaToVertexTheory"));
1622 fhCutStatistics = dynamic_cast<TH1F*> (gDirectory->Get("cut_statistics"));
1623 fhCutCorrelation = dynamic_cast<TH2F*> (gDirectory->Get("cut_correlation"));
1625 for (Int_t i=0; i<2; i++) {
1628 gDirectory->cd("before_cuts");
1631 gDirectory->cd("after_cuts");
1633 fhNClustersITS[i] = dynamic_cast<TH1F*> (gDirectory->Get("nClustersITS" ));
1634 fhNClustersTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("nClustersTPC" ));
1635 fhNSharedClustersTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("nSharedClustersTPC" ));
1636 fhNCrossedRowsTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("nCrossedRowsTPC" ));
1637 fhRatioCrossedRowsOverFindableClustersTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("ratioCrossedRowsOverFindableClustersTPC" ));
1638 fhChi2PerClusterITS[i] = dynamic_cast<TH1F*> (gDirectory->Get("chi2PerClusterITS"));
1639 fhChi2PerClusterTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("chi2PerClusterTPC"));
1640 fhChi2TPCConstrainedVsGlobal[i] = dynamic_cast<TH1F*> (gDirectory->Get("fhChi2TPCConstrainedVsGlobal"));
1641 fhNClustersForITSPID[i] = dynamic_cast<TH1F*> (gDirectory->Get("nPointsForITSpid"));
1642 fhNMissingITSPoints[i] = dynamic_cast<TH1F*> (gDirectory->Get("nMissingITSClusters"));
1644 fhC11[i] = dynamic_cast<TH1F*> (gDirectory->Get("covMatrixDiagonal11"));
1645 fhC22[i] = dynamic_cast<TH1F*> (gDirectory->Get("covMatrixDiagonal22"));
1646 fhC33[i] = dynamic_cast<TH1F*> (gDirectory->Get("covMatrixDiagonal33"));
1647 fhC44[i] = dynamic_cast<TH1F*> (gDirectory->Get("covMatrixDiagonal44"));
1648 fhC55[i] = dynamic_cast<TH1F*> (gDirectory->Get("covMatrixDiagonal55"));
1650 fhRel1PtUncertainty[i] = dynamic_cast<TH1F*> (gDirectory->Get("rel1PtUncertainty"));
1652 fhDXY[i] = dynamic_cast<TH1F*> (gDirectory->Get("dXY" ));
1653 fhDZ[i] = dynamic_cast<TH1F*> (gDirectory->Get("dZ" ));
1654 fhDXYDZ[i] = dynamic_cast<TH1F*> (gDirectory->Get("dXYDZ"));
1655 fhDXYvsDZ[i] = dynamic_cast<TH2F*> (gDirectory->Get("dXYvsDZ"));
1657 fhDXYNormalized[i] = dynamic_cast<TH1F*> (gDirectory->Get("dXYNormalized" ));
1658 fhDZNormalized[i] = dynamic_cast<TH1F*> (gDirectory->Get("dZNormalized" ));
1659 fhDXYvsDZNormalized[i] = dynamic_cast<TH2F*> (gDirectory->Get("dXYvsDZNormalized"));
1660 fhNSigmaToVertex[i] = dynamic_cast<TH1F*> (gDirectory->Get("nSigmaToVertex"));
1662 fhPt[i] = dynamic_cast<TH1F*> (gDirectory->Get("pt"));
1663 fhEta[i] = dynamic_cast<TH1F*> (gDirectory->Get("eta"));
1665 gDirectory->cd("../");
1668 gDirectory->cd("..");
1673 //____________________________________________________________________
1674 void AliESDtrackCuts::SaveHistograms(const Char_t* dir) {
1676 // saves the histograms in a directory (dir)
1679 if (!fHistogramsOn) {
1680 AliDebug(0, "Histograms not on - cannot save histograms!!!");
1687 gDirectory->mkdir(dir);
1688 gDirectory->cd(dir);
1690 gDirectory->mkdir("before_cuts");
1691 gDirectory->mkdir("after_cuts");
1693 // a factor of 2 is needed since n sigma is positive
1694 ffDTheoretical->SetParameter(0,2*fhNSigmaToVertex[0]->Integral("width"));
1695 ffDTheoretical->Write("nSigmaToVertexTheory");
1697 fhCutStatistics->Write();
1698 fhCutCorrelation->Write();
1700 for (Int_t i=0; i<2; i++) {
1702 gDirectory->cd("before_cuts");
1704 gDirectory->cd("after_cuts");
1706 fhNClustersITS[i] ->Write();
1707 fhNClustersTPC[i] ->Write();
1708 fhNSharedClustersTPC[i] ->Write();
1709 fhNCrossedRowsTPC[i] ->Write();
1710 fhRatioCrossedRowsOverFindableClustersTPC[i] ->Write();
1711 fhChi2PerClusterITS[i] ->Write();
1712 fhChi2PerClusterTPC[i] ->Write();
1713 fhChi2TPCConstrainedVsGlobal[i] ->Write();
1714 fhNClustersForITSPID[i] ->Write();
1715 fhNMissingITSPoints[i] ->Write();
1723 fhRel1PtUncertainty[i] ->Write();
1727 fhDXYDZ[i] ->Write();
1728 fhDXYvsDZ[i] ->Write();
1730 fhDXYNormalized[i] ->Write();
1731 fhDZNormalized[i] ->Write();
1732 fhDXYvsDZNormalized[i] ->Write();
1733 fhNSigmaToVertex[i] ->Write();
1738 gDirectory->cd("../");
1741 gDirectory->cd("../");
1744 //____________________________________________________________________
1745 void AliESDtrackCuts::DrawHistograms()
1747 // draws some histograms
1749 TCanvas* canvas1 = new TCanvas(Form("%s_1", GetName()), "Track Quality Results1", 800, 800);
1750 canvas1->Divide(2, 2);
1753 fhNClustersTPC[0]->SetStats(kFALSE);
1754 fhNClustersTPC[0]->Draw();
1757 fhChi2PerClusterTPC[0]->SetStats(kFALSE);
1758 fhChi2PerClusterTPC[0]->Draw();
1761 fhNSigmaToVertex[0]->SetStats(kFALSE);
1762 fhNSigmaToVertex[0]->GetXaxis()->SetRangeUser(0, 10);
1763 fhNSigmaToVertex[0]->Draw();
1765 canvas1->SaveAs(Form("%s_%s.gif", GetName(), canvas1->GetName()));
1767 TCanvas* canvas2 = new TCanvas(Form("%s_2", GetName()), "Track Quality Results2", 1200, 800);
1768 canvas2->Divide(3, 2);
1771 fhC11[0]->SetStats(kFALSE);
1776 fhC22[0]->SetStats(kFALSE);
1781 fhC33[0]->SetStats(kFALSE);
1786 fhC44[0]->SetStats(kFALSE);
1791 fhC55[0]->SetStats(kFALSE);
1796 fhRel1PtUncertainty[0]->SetStats(kFALSE);
1798 fhRel1PtUncertainty[0]->Draw();
1800 canvas2->SaveAs(Form("%s_%s.gif", GetName(), canvas2->GetName()));
1802 TCanvas* canvas3 = new TCanvas(Form("%s_3", GetName()), "Track Quality Results3", 1200, 800);
1803 canvas3->Divide(3, 2);
1806 fhDXY[0]->SetStats(kFALSE);
1811 fhDZ[0]->SetStats(kFALSE);
1816 fhDXYvsDZ[0]->SetStats(kFALSE);
1818 gPad->SetRightMargin(0.15);
1819 fhDXYvsDZ[0]->Draw("COLZ");
1822 fhDXYNormalized[0]->SetStats(kFALSE);
1824 fhDXYNormalized[0]->Draw();
1827 fhDZNormalized[0]->SetStats(kFALSE);
1829 fhDZNormalized[0]->Draw();
1832 fhDXYvsDZNormalized[0]->SetStats(kFALSE);
1834 gPad->SetRightMargin(0.15);
1835 fhDXYvsDZNormalized[0]->Draw("COLZ");
1837 canvas3->SaveAs(Form("%s_%s.gif", GetName(), canvas3->GetName()));
1839 TCanvas* canvas4 = new TCanvas(Form("%s_4", GetName()), "Track Quality Results4", 800, 500);
1840 canvas4->Divide(2, 1);
1843 fhCutStatistics->SetStats(kFALSE);
1844 fhCutStatistics->LabelsOption("v");
1845 gPad->SetBottomMargin(0.3);
1846 fhCutStatistics->Draw();
1849 fhCutCorrelation->SetStats(kFALSE);
1850 fhCutCorrelation->LabelsOption("v");
1851 gPad->SetBottomMargin(0.3);
1852 gPad->SetLeftMargin(0.3);
1853 fhCutCorrelation->Draw("COLZ");
1855 canvas4->SaveAs(Form("%s_%s.gif", GetName(), canvas4->GetName()));
1858 fhDXYvsDZNormalized[0]->SetStats(kFALSE);
1859 fhDXYvsDZNormalized[0]->DrawCopy("COLZ");
1862 fhNClustersTPC[0]->SetStats(kFALSE);
1863 fhNClustersTPC[0]->DrawCopy();
1866 fhChi2PerClusterITS[0]->SetStats(kFALSE);
1867 fhChi2PerClusterITS[0]->DrawCopy();
1868 fhChi2PerClusterITS[1]->SetLineColor(2);
1869 fhChi2PerClusterITS[1]->DrawCopy("SAME");
1872 fhChi2PerClusterTPC[0]->SetStats(kFALSE);
1873 fhChi2PerClusterTPC[0]->DrawCopy();
1874 fhChi2PerClusterTPC[1]->SetLineColor(2);
1875 fhChi2PerClusterTPC[1]->DrawCopy("SAME");*/
1877 //--------------------------------------------------------------------------
1878 void AliESDtrackCuts::SetPtDepDCACuts(Double_t pt) {
1880 // set the pt-dependent DCA cuts
1883 if(f1CutMaxDCAToVertexXYPtDep) {
1884 fCutMaxDCAToVertexXY=f1CutMaxDCAToVertexXYPtDep->Eval(pt);
1887 if(f1CutMaxDCAToVertexZPtDep) {
1888 fCutMaxDCAToVertexZ=f1CutMaxDCAToVertexZPtDep->Eval(pt);
1891 if(f1CutMinDCAToVertexXYPtDep) {
1892 fCutMinDCAToVertexXY=f1CutMinDCAToVertexXYPtDep->Eval(pt);
1895 if(f1CutMinDCAToVertexZPtDep) {
1896 fCutMinDCAToVertexZ=f1CutMinDCAToVertexZPtDep->Eval(pt);
1905 //--------------------------------------------------------------------------
1906 Bool_t AliESDtrackCuts::CheckPtDepDCA(TString dist,Bool_t print) const {
1908 // Check the correctness of the string syntax
1910 Bool_t retval=kTRUE;
1912 if(!dist.Contains("pt")) {
1913 if(print) AliError("string must contain \"pt\"");
1919 void AliESDtrackCuts::SetMaxDCAToVertexXYPtDep(const char *dist){
1921 if(f1CutMaxDCAToVertexXYPtDep){
1922 delete f1CutMaxDCAToVertexXYPtDep;
1924 f1CutMaxDCAToVertexXYPtDep = 0;
1925 fCutMaxDCAToVertexXYPtDep = "";
1927 if(!CheckPtDepDCA(dist,kTRUE)){
1930 fCutMaxDCAToVertexXYPtDep = dist;
1932 tmp.ReplaceAll("pt","x");
1933 f1CutMaxDCAToVertexXYPtDep = new TFormula("f1CutMaxDCAToVertexXYPtDep",tmp.Data());
1937 void AliESDtrackCuts::SetMaxDCAToVertexZPtDep(const char *dist){
1940 if(f1CutMaxDCAToVertexZPtDep){
1941 delete f1CutMaxDCAToVertexZPtDep;
1943 f1CutMaxDCAToVertexZPtDep = 0;
1944 fCutMaxDCAToVertexZPtDep = "";
1946 if(!CheckPtDepDCA(dist,kTRUE))return;
1948 fCutMaxDCAToVertexZPtDep = dist;
1950 tmp.ReplaceAll("pt","x");
1951 f1CutMaxDCAToVertexZPtDep = new TFormula("f1CutMaxDCAToVertexZPtDep",tmp.Data());
1957 void AliESDtrackCuts::SetMinDCAToVertexXYPtDep(const char *dist){
1960 if(f1CutMinDCAToVertexXYPtDep){
1961 delete f1CutMinDCAToVertexXYPtDep;
1963 f1CutMinDCAToVertexXYPtDep = 0;
1964 fCutMinDCAToVertexXYPtDep = "";
1966 if(!CheckPtDepDCA(dist,kTRUE))return;
1968 fCutMinDCAToVertexXYPtDep = dist;
1970 tmp.ReplaceAll("pt","x");
1971 f1CutMinDCAToVertexXYPtDep = new TFormula("f1CutMinDCAToVertexXYPtDep",tmp.Data());
1976 void AliESDtrackCuts::SetMinDCAToVertexZPtDep(const char *dist){
1980 if(f1CutMinDCAToVertexZPtDep){
1981 delete f1CutMinDCAToVertexZPtDep;
1983 f1CutMinDCAToVertexZPtDep = 0;
1984 fCutMinDCAToVertexZPtDep = "";
1986 if(!CheckPtDepDCA(dist,kTRUE))return;
1987 fCutMinDCAToVertexZPtDep = dist;
1989 tmp.ReplaceAll("pt","x");
1990 f1CutMinDCAToVertexZPtDep = new TFormula("f1CutMinDCAToVertexZPtDep",tmp.Data());
1993 AliESDtrackCuts* AliESDtrackCuts::GetMultEstTrackCuts(MultEstTrackCuts cut)
1995 // returns the multiplicity estimator track cuts objects to allow for user configuration
1996 // upon first call the objects are created
1998 // the cut defined here correspond to GetStandardITSTPCTrackCuts2010 (apart from the one for without SPD)
2000 if (!fgMultEstTrackCuts[kMultEstTrackCutGlobal])
2002 // quality cut on ITS+TPC tracks
2003 fgMultEstTrackCuts[kMultEstTrackCutGlobal] = new AliESDtrackCuts();
2004 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetMinNClustersTPC(70);
2005 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetMaxChi2PerClusterTPC(4);
2006 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetAcceptKinkDaughters(kFALSE);
2007 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetRequireTPCRefit(kTRUE);
2008 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetRequireITSRefit(kTRUE);
2009 //multiplicity underestimate if we use global tracks with |eta| > 0.9
2010 fgMultEstTrackCuts[kMultEstTrackCutGlobal]->SetEtaRange(-0.9, 0.9);
2012 // quality cut on ITS_SA tracks (complementary to ITS+TPC)
2013 fgMultEstTrackCuts[kMultEstTrackCutITSSA] = new AliESDtrackCuts();
2014 fgMultEstTrackCuts[kMultEstTrackCutITSSA]->SetRequireITSRefit(kTRUE);
2016 // primary selection for tracks with SPD hits
2017 fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD] = new AliESDtrackCuts();
2018 fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->SetClusterRequirementITS(AliESDtrackCuts::kSPD, AliESDtrackCuts::kAny);
2019 fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->SetMaxDCAToVertexXYPtDep("0.0182+0.0350/pt^1.01");
2020 fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->SetMaxDCAToVertexZ(2);
2022 // primary selection for tracks w/o SPD hits
2023 fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD] = new AliESDtrackCuts();
2024 fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->SetClusterRequirementITS(AliESDtrackCuts::kSPD, AliESDtrackCuts::kNone);
2025 fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->SetMaxDCAToVertexXYPtDep("1.5*(0.0182+0.0350/pt^1.01)");
2026 fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->SetMaxDCAToVertexZ(2);
2029 return fgMultEstTrackCuts[cut];
2032 Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstTrackType trackType, Float_t etaRange)
2034 // Get multiplicity estimate based on TPC/ITS tracks and tracklets
2035 // Adapted for AliESDtrackCuts from a version developed by: Ruben Shahoyan, Anton Alkin, Arvinder Palaha
2037 // Returns a negative value if no reliable estimate can be provided:
2038 // -1 SPD vertex missing
2039 // -2 SPD VertexerZ dispersion too large
2040 // -3 Track vertex missing (not checked for kTracklets)
2041 // -4 Distance between SPD and track vertices too large (not checked for kTracklets)
2043 // WARNING This functions does not cut on the z vtx. Depending on the eta range requested, you need to restrict your z vertex range!
2045 // Strategy for combined estimators
2046 // 1. Count global tracks and flag them
2047 // 2. Count ITSSA as complementaries for ITSTPC+ or as main tracks
2048 // 3. Count the complementary SPD tracklets
2050 const AliESDVertex* vertices[2];
2051 vertices[0] = esd->GetPrimaryVertexSPD();
2052 vertices[1] = esd->GetPrimaryVertexTracks();
2054 if (!vertices[0]->GetStatus())
2056 AliDebugClass(AliLog::kDebug, "No SPD vertex. Not able to make a reliable multiplicity estimate.");
2060 if (vertices[0]->IsFromVertexerZ() && vertices[0]->GetDispersion() > 0.02)
2062 AliDebugClass(AliLog::kDebug, "Vertexer z dispersion > 0.02. Not able to make a reliable multiplicity estimate.");
2066 Int_t multiplicityEstimate = 0;
2068 // SPD tracklet-only estimate
2069 if (trackType == kTracklets)
2071 const AliMultiplicity* spdmult = esd->GetMultiplicity(); // spd multiplicity object
2072 for (Int_t i=0; i<spdmult->GetNumberOfTracklets(); ++i)
2074 if (TMath::Abs(spdmult->GetEta(i)) > etaRange)
2075 continue; // eta selection for tracklets
2076 multiplicityEstimate++;
2078 return multiplicityEstimate;
2081 if (!vertices[1]->GetStatus())
2083 AliDebugClass(AliLog::kDebug, "No track vertex. Not able to make a reliable multiplicity estimate.");
2087 // TODO value of displacement to be studied
2088 const Float_t maxDisplacement = 0.5;
2089 //check for displaced vertices
2090 Double_t displacement = TMath::Abs(vertices[0]->GetZ() - vertices[1]->GetZ());
2091 if (displacement > maxDisplacement)
2093 AliDebugClass(AliLog::kDebug, Form("Displaced vertices %f > %f",displacement,maxDisplacement));
2097 // update eta range in track cuts
2098 GetMultEstTrackCuts(kMultEstTrackCutITSSA)->SetEtaRange(-etaRange, etaRange);
2099 GetMultEstTrackCuts(kMultEstTrackCutDCAwSPD)->SetEtaRange(-etaRange, etaRange);
2100 GetMultEstTrackCuts(kMultEstTrackCutDCAwoSPD)->SetEtaRange(-etaRange, etaRange);
2102 //*******************************************************************************************************
2103 //set counters to initial zeros
2104 Int_t tracksITSTPC = 0; //number of global tracks for a given event
2105 Int_t tracksITSSA = 0; //number of ITS standalone tracks for a given event
2106 Int_t tracksITSTPCSA_complementary = 0; //number of ITS standalone tracks complementary to TPC for a given event
2107 Int_t trackletsITSTPC_complementary = 0;//number of SPD tracklets complementary to global/ITSSA tracks for a given events
2108 Int_t trackletsITSSA_complementary = 0; //number of SPD tracklets complementary to ITSSA tracks for a given event
2110 const Int_t nESDTracks = esd->GetNumberOfTracks();
2111 Int_t highestID = 0;
2113 // flags for secondary and rejected tracks
2114 const Int_t kRejBit = BIT(15); // set this bit in global tracks if it is rejected by a cut
2115 const Int_t kSecBit = BIT(16); // set this bit in global tracks if it is secondary according to a cut
2117 for(Int_t itracks=0; itracks < nESDTracks; itracks++) {
2118 if(esd->GetTrack(itracks)->GetLabel() > highestID) highestID = esd->GetTrack(itracks)->GetLabel();
2119 esd->GetTrack(itracks)->ResetBit(kSecBit|kRejBit); //reset bits used for flagging secondaries and rejected tracks in case they were changed before this analysis
2121 const Int_t maxid = highestID+1; // used to define bool array for check multiple associations of tracklets to one track. array starts at 0.
2123 // bit mask for esd tracks, to check if multiple tracklets are associated to it
2124 Bool_t globalBits[maxid], pureITSBits[maxid];
2125 for(Int_t i=0; i<maxid; i++){ // set all bools to false
2126 globalBits[i]=kFALSE;
2127 pureITSBits[i]=kFALSE;
2130 //*******************************************************************************************************
2131 // get multiplicity from global tracks
2132 for(Int_t itracks = 0; itracks < nESDTracks; itracks++) { // flag the tracks
2133 AliESDtrack* track = esd->GetTrack(itracks);
2135 // if track is a secondary from a V0, flag as a secondary
2136 if (track->IsOn(AliESDtrack::kMultInV0)) {
2137 track->SetBit(kSecBit);
2142 if (track->IsOn(AliESDtrack::kMultSec)) {
2143 track->SetBit(kSecBit);
2147 // check tracks with ITS part
2148 //*******************************************************************************************************
2149 if (track->IsOn(AliESDtrack::kITSin) && !track->IsOn(AliESDtrack::kITSpureSA) && trackType == kTrackletsITSTPC) { // track has ITS part but is not an ITS_SA
2150 //*******************************************************************************************************
2152 if (track->IsOn(AliESDtrack::kTPCin)) { // Global track, has ITS and TPC contributions
2153 if (fgMultEstTrackCuts[kMultEstTrackCutGlobal]->AcceptTrack(track)) { // good ITSTPC track
2154 if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
2155 tracksITSTPC++; //global track counted
2156 globalBits[itracks] = kTRUE;
2158 else track->SetBit(kSecBit); // large DCA -> secondary, don't count either track not associated tracklet
2160 else track->SetBit(kRejBit); // bad quality, don't count the track, but may count tracklet if associated
2162 //*******************************************************************************************************
2163 // ITS complementary
2164 else if (fgMultEstTrackCuts[kMultEstTrackCutITSSA]->AcceptTrack(track)) { // good ITS complementary track
2165 if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
2166 tracksITSTPCSA_complementary++;
2167 globalBits[itracks] = kTRUE;
2169 else track->SetBit(kSecBit); // large DCA -> secondary, don't count either track not associated tracklet
2171 else track->SetBit(kRejBit); // bad quality, don't count the track, but may count tracklet if associated
2173 //*******************************************************************************************************
2174 // check tracks from ITS_SA_PURE
2175 if (track->IsOn(AliESDtrack::kITSin) && track->IsOn(AliESDtrack::kITSpureSA) && trackType == kTrackletsITSSA){
2176 if (fgMultEstTrackCuts[kMultEstTrackCutITSSA]->AcceptTrack(track)) { // good ITSSA track
2177 if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
2179 pureITSBits[itracks] = kTRUE;
2181 else track->SetBit(kRejBit);
2183 else track->SetBit(kRejBit);
2185 }//ESD tracks counted
2187 //*******************************************************************************************************
2188 // get multiplicity from ITS tracklets to complement TPC+ITS, and ITSpureSA
2189 const AliMultiplicity* spdmult = esd->GetMultiplicity(); // spd multiplicity object
2190 for (Int_t i=0; i<spdmult->GetNumberOfTracklets(); ++i) {
2191 if (TMath::Abs(spdmult->GetEta(i)) > etaRange) continue; // eta selection for tracklets
2193 // if counting tracks+tracklets, check if clusters were already used in tracks
2194 Int_t id1,id2,id3,id4;
2195 spdmult->GetTrackletTrackIDs(i,0,id1,id2); // references for eventual Global/ITS_SA tracks
2196 AliESDtrack* tr1 = id1>=0 ? esd->GetTrack(id1) : 0;
2197 spdmult->GetTrackletTrackIDs(i,1,id3,id4); // references for eventual ITS_SA_pure tracks
2198 AliESDtrack* tr3 = id3>=0 ? esd->GetTrack(id3) : 0;
2200 // are both clusters from the same tracks? If not, skip the tracklet (shouldn't change things much)
2201 if ((id1!=id2 && id1>=0 && id2>=0) || (id3!=id4 && id3>=0 && id4>=0)) continue;
2203 Bool_t bUsedInGlobal = (id1 != -1) ? globalBits[id1] : 0;// has associated global track been associated to a previous tracklet?
2204 Bool_t bUsedInPureITS = (id3 != -1) ? pureITSBits[id3] : 0;// has associated pure ITS track been associated to a previous tracklet?
2205 //*******************************************************************************************************
2206 if (trackType == kTrackletsITSTPC) {
2207 // count tracklets towards global+complementary tracks
2208 if ( (tr1 && !tr1->TestBit(kSecBit)) && // reject as secondary
2209 (tr1 && tr1->TestBit(kRejBit)) ) { // count tracklet as bad quality track
2211 ++trackletsITSTPC_complementary;
2212 if(id1>0) globalBits[id1] = kTRUE; // mark global track linked to this tracklet as "associated"
2216 ++trackletsITSTPC_complementary; // if no associated track, count the tracklet
2219 // count tracklets towards ITS_SA_pure tracks
2220 if ( (tr3 && !tr3->TestBit(kSecBit)) && // reject as secondary
2221 (tr3 && tr3->TestBit(kRejBit)) ) { // count tracklet as bad quality track
2222 if(!bUsedInPureITS) {
2223 ++trackletsITSSA_complementary;
2224 if(id3>0) pureITSBits[id3] = kTRUE; // mark global track linked to this tracklet as "associated"
2228 ++trackletsITSSA_complementary; // if no associated track, count the tracklet
2233 //*******************************************************************************************************
2234 if (trackType == kTrackletsITSTPC)
2235 multiplicityEstimate = tracksITSTPC + tracksITSTPCSA_complementary + trackletsITSTPC_complementary;
2237 multiplicityEstimate = tracksITSSA + trackletsITSSA_complementary;
2239 return multiplicityEstimate;