]> git.uio.no Git - u/mrichter/AliRoot.git/blobdiff - ANALYSIS/AliESDtrackCuts.cxx
Implement comparison of sim and rec CDB's, by default for the TPC/RecoParam only
[u/mrichter/AliRoot.git] / ANALYSIS / AliESDtrackCuts.cxx
index 716c3d99466caefb250a7f83f13216ac9a017c57..7478692e524a12729860b287c0933ff1870f1712 100644 (file)
@@ -28,6 +28,7 @@
 #include <TDirectory.h>
 #include <TH2F.h>
 #include <TF1.h>
+#include <TBits.h>
 
 //____________________________________________________________________
 ClassImp(AliESDtrackCuts)
@@ -72,10 +73,15 @@ const Char_t* AliESDtrackCuts::fgkCutNames[kNCuts] = {
  "require ITS Pid",
  "n crossed rows TPC",
  "n crossed rows / n findable clusters",
- "missing ITS points"
+ "missing ITS points",
+ "#Chi^{2} TPC constrained vs. global",
+ "require TOF out",
+ "TOF Distance cut",
+ "min length in active volume TPC"
 };
 
 AliESDtrackCuts* AliESDtrackCuts::fgMultEstTrackCuts[AliESDtrackCuts::kNMultEstTrackCuts] = { 0, 0, 0, 0 };
+Char_t AliESDtrackCuts::fgBeamTypeFlag = -1;
 
 //____________________________________________________________________
 AliESDtrackCuts::AliESDtrackCuts(const Char_t* name, const Char_t* title) : AliAnalysisCuts(name,title),
@@ -83,8 +89,13 @@ AliESDtrackCuts::AliESDtrackCuts(const Char_t* name, const Char_t* title) : AliA
   fCutMinNClusterITS(0),
   fCutMinNCrossedRowsTPC(0),
   fCutMinRatioCrossedRowsOverFindableClustersTPC(0),
+  f1CutMinNClustersTPCPtDep(0x0),
+  fCutMaxPtDepNClustersTPC(0),
+  fCutMinLengthActiveVolumeTPC(0),
   fCutMaxChi2PerClusterTPC(0),
   fCutMaxChi2PerClusterITS(0),
+  fCutMaxChi2TPCConstrainedVsGlobal(0),
+  fCutMaxChi2TPCConstrainedVsGlobalVertexType(kVertexTracks | kVertexSPD),
   fCutMaxMissingITSPoints(0),
   fCutMaxC11(0),
   fCutMaxC22(0),
@@ -130,6 +141,9 @@ AliESDtrackCuts::AliESDtrackCuts(const Char_t* name, const Char_t* title) : AliA
   fEtaMax(0),
   fRapMin(0),
   fRapMax(0),
+  fCutRequireTOFout(kFALSE),
+  fFlagCutTOFdistance(kFALSE),
+  fCutTOFdistance(3.),
   fHistogramsOn(0),
   ffDTheoretical(0),
   fhCutStatistics(0),         
@@ -148,7 +162,9 @@ AliESDtrackCuts::AliESDtrackCuts(const Char_t* name, const Char_t* title) : AliA
   SetMinNCrossedRowsTPC();
   SetMinRatioCrossedRowsOverFindableClustersTPC();
   SetMaxChi2PerClusterTPC();
-  SetMaxChi2PerClusterITS();                               
+  SetMaxChi2PerClusterITS();
+  SetMaxChi2TPCConstrainedGlobal();
+  SetMaxChi2TPCConstrainedGlobalVertexType();
   SetMaxNOfMissingITSPoints();
   SetMaxCovDiagonalElements();
   SetMaxRel1PtUncertainty();
@@ -187,8 +203,13 @@ AliESDtrackCuts::AliESDtrackCuts(const AliESDtrackCuts &c) : AliAnalysisCuts(c),
   fCutMinNClusterITS(0),
   fCutMinNCrossedRowsTPC(0),
   fCutMinRatioCrossedRowsOverFindableClustersTPC(0),
+  f1CutMinNClustersTPCPtDep(0x0),
+  fCutMaxPtDepNClustersTPC(0),
+  fCutMinLengthActiveVolumeTPC(0),
   fCutMaxChi2PerClusterTPC(0),
   fCutMaxChi2PerClusterITS(0),
+  fCutMaxChi2TPCConstrainedVsGlobal(0),
+  fCutMaxChi2TPCConstrainedVsGlobalVertexType(kVertexTracks | kVertexSPD),
   fCutMaxMissingITSPoints(0),
   fCutMaxC11(0),
   fCutMaxC22(0),
@@ -234,9 +255,12 @@ AliESDtrackCuts::AliESDtrackCuts(const AliESDtrackCuts &c) : AliAnalysisCuts(c),
   fEtaMax(0),
   fRapMin(0),
   fRapMax(0),
+  fCutRequireTOFout(kFALSE),
+  fFlagCutTOFdistance(kFALSE),
+  fCutTOFdistance(3.),
   fHistogramsOn(0),
-  ffDTheoretical(0),                                
-  fhCutStatistics(0),         
+  ffDTheoretical(0),
+  fhCutStatistics(0),
   fhCutCorrelation(0)
 {
   //
@@ -268,6 +292,8 @@ AliESDtrackCuts::~AliESDtrackCuts()
       delete fhChi2PerClusterITS[i];       
     if (fhChi2PerClusterTPC[i])
       delete fhChi2PerClusterTPC[i];    
+    if (fhChi2TPCConstrainedVsGlobal[i])
+      delete fhChi2TPCConstrainedVsGlobal[i];
     if(fhNClustersForITSPID[i])
       delete fhNClustersForITSPID[i];
     if(fhNMissingITSPoints[i])
@@ -307,6 +333,8 @@ AliESDtrackCuts::~AliESDtrackCuts()
       delete fhPt[i];
     if (fhEta[i])
       delete fhEta[i];
+    if (fhTOFdistance[i])
+      delete fhTOFdistance[i];
   }
 
   if(f1CutMaxDCAToVertexXYPtDep)delete f1CutMaxDCAToVertexXYPtDep;
@@ -325,7 +353,11 @@ AliESDtrackCuts::~AliESDtrackCuts()
   if (fhCutStatistics)
     delete fhCutStatistics;             
   if (fhCutCorrelation)
-    delete fhCutCorrelation;            
+    delete fhCutCorrelation;    
+
+  if(f1CutMinNClustersTPCPtDep)
+    delete f1CutMinNClustersTPCPtDep;
+        
 }
 
 void AliESDtrackCuts::Init()
@@ -339,6 +371,8 @@ void AliESDtrackCuts::Init()
 
   fCutMaxChi2PerClusterTPC = 0;
   fCutMaxChi2PerClusterITS = 0;
+  fCutMaxChi2TPCConstrainedVsGlobal = 0;
+  fCutMaxChi2TPCConstrainedVsGlobalVertexType = kVertexTracks | kVertexSPD;
   fCutMaxMissingITSPoints  = 0;
   
   for (Int_t i = 0; i < 3; i++)
@@ -413,6 +447,7 @@ void AliESDtrackCuts::Init()
 
     fhChi2PerClusterITS[i] = 0;
     fhChi2PerClusterTPC[i] = 0;
+    fhChi2TPCConstrainedVsGlobal[i] = 0;
     fhNClustersForITSPID[i] = 0;
     fhNMissingITSPoints[i] = 0;
 
@@ -436,6 +471,7 @@ void AliESDtrackCuts::Init()
     
     fhPt[i] = 0;
     fhEta[i] = 0;
+    fhTOFdistance[i] = 0;
   }
   ffDTheoretical = 0;
 
@@ -469,10 +505,16 @@ void AliESDtrackCuts::Copy(TObject &c) const
   target.fCutMinNClusterITS = fCutMinNClusterITS;
   target.fCutMinNCrossedRowsTPC = fCutMinNCrossedRowsTPC;
   target.fCutMinRatioCrossedRowsOverFindableClustersTPC = fCutMinRatioCrossedRowsOverFindableClustersTPC;
-
-
+  if(f1CutMinNClustersTPCPtDep){
+    target.f1CutMinNClustersTPCPtDep = (TFormula*) f1CutMinNClustersTPCPtDep->Clone("f1CutMinNClustersTPCPtDep");
+  }
+  target.fCutMaxPtDepNClustersTPC =   fCutMaxPtDepNClustersTPC;
+  target.fCutMinLengthActiveVolumeTPC = fCutMinLengthActiveVolumeTPC;
+  
   target.fCutMaxChi2PerClusterTPC = fCutMaxChi2PerClusterTPC;
   target.fCutMaxChi2PerClusterITS = fCutMaxChi2PerClusterITS;
+  target.fCutMaxChi2TPCConstrainedVsGlobal = fCutMaxChi2TPCConstrainedVsGlobal;
+  target.fCutMaxChi2TPCConstrainedVsGlobalVertexType = fCutMaxChi2TPCConstrainedVsGlobalVertexType;
   target.fCutMaxMissingITSPoints = fCutMaxMissingITSPoints;
 
   for (Int_t i = 0; i < 3; i++)
@@ -505,16 +547,16 @@ void AliESDtrackCuts::Copy(TObject &c) const
   target.fCutMinDCAToVertexZ = fCutMinDCAToVertexZ;
 
   target.fCutMaxDCAToVertexXYPtDep = fCutMaxDCAToVertexXYPtDep;
-  target.SetMaxDCAToVertexXYPtDep(fCutMaxDCAToVertexXYPtDep.Data());
+  if(fCutMaxDCAToVertexXYPtDep.Length()>0)target.SetMaxDCAToVertexXYPtDep(fCutMaxDCAToVertexXYPtDep.Data());
 
   target.fCutMaxDCAToVertexZPtDep = fCutMaxDCAToVertexZPtDep;
-  target.SetMaxDCAToVertexZPtDep(fCutMaxDCAToVertexZPtDep.Data());
+  if(fCutMaxDCAToVertexZPtDep.Length()>0)target.SetMaxDCAToVertexZPtDep(fCutMaxDCAToVertexZPtDep.Data());
 
   target.fCutMinDCAToVertexXYPtDep = fCutMinDCAToVertexXYPtDep;
-  target.SetMinDCAToVertexXYPtDep(fCutMinDCAToVertexXYPtDep.Data());
+  if(fCutMinDCAToVertexXYPtDep.Length()>0)target.SetMinDCAToVertexXYPtDep(fCutMinDCAToVertexXYPtDep.Data());
 
   target.fCutMinDCAToVertexZPtDep = fCutMinDCAToVertexZPtDep;
-  target.SetMinDCAToVertexZPtDep(fCutMinDCAToVertexZPtDep.Data());
+  if(fCutMinDCAToVertexZPtDep.Length()>0)target.SetMinDCAToVertexZPtDep(fCutMinDCAToVertexZPtDep.Data());
 
   target.fPMin = fPMin;
   target.fPMax = fPMax;
@@ -531,6 +573,10 @@ void AliESDtrackCuts::Copy(TObject &c) const
   target.fRapMin = fRapMin;
   target.fRapMax = fRapMax;
 
+  target.fFlagCutTOFdistance = fFlagCutTOFdistance;
+  target.fCutTOFdistance = fCutTOFdistance;
+  target.fCutRequireTOFout = fCutRequireTOFout;
+
   target.fHistogramsOn = fHistogramsOn;
 
   for (Int_t i=0; i<2; ++i)
@@ -543,6 +589,7 @@ void AliESDtrackCuts::Copy(TObject &c) const
 
     if (fhChi2PerClusterITS[i]) target.fhChi2PerClusterITS[i] = (TH1F*) fhChi2PerClusterITS[i]->Clone();
     if (fhChi2PerClusterTPC[i]) target.fhChi2PerClusterTPC[i] = (TH1F*) fhChi2PerClusterTPC[i]->Clone();
+    if (fhChi2TPCConstrainedVsGlobal[i]) target.fhChi2TPCConstrainedVsGlobal[i] = (TH1F*) fhChi2TPCConstrainedVsGlobal[i]->Clone();
     if (fhNClustersForITSPID[i]) target.fhNClustersForITSPID[i] = (TH1F*) fhNClustersForITSPID[i]->Clone();
     if (fhNMissingITSPoints[i]) target.fhNMissingITSPoints[i] = (TH1F*) fhNMissingITSPoints[i]->Clone();
 
@@ -566,6 +613,7 @@ void AliESDtrackCuts::Copy(TObject &c) const
     
     if (fhPt[i]) target.fhPt[i] = (TH1F*) fhPt[i]->Clone();
     if (fhEta[i]) target.fhEta[i] = (TH1F*) fhEta[i]->Clone();
+    if (fhTOFdistance[i]) target.fhTOFdistance[i] = (TH2F*) fhTOFdistance[i]->Clone();
   }
   if (ffDTheoretical) target.ffDTheoretical = (TF1*) ffDTheoretical->Clone();
 
@@ -612,6 +660,8 @@ Long64_t AliESDtrackCuts::Merge(TCollection* list) {
                                                                    
       fhChi2PerClusterITS[i] ->Add(entry->fhChi2PerClusterITS[i]); 
       fhChi2PerClusterTPC[i] ->Add(entry->fhChi2PerClusterTPC[i]); 
+      if (fhChi2TPCConstrainedVsGlobal[i])
+       fhChi2TPCConstrainedVsGlobal[i]->Add(entry->fhChi2TPCConstrainedVsGlobal[i]);
       if (fhNClustersForITSPID[i])
        fhNClustersForITSPID[i]->Add(entry->fhNClustersForITSPID[i]);
       if (fhNMissingITSPoints[i])
@@ -637,6 +687,7 @@ Long64_t AliESDtrackCuts::Merge(TCollection* list) {
 
       fhPt[i]                ->Add(entry->fhPt[i]); 
       fhEta[i]               ->Add(entry->fhEta[i]); 
+      fhTOFdistance[i]       ->Add(entry->fhTOFdistance[i]); 
     }      
 
     fhCutStatistics  ->Add(entry->fhCutStatistics);        
@@ -647,6 +698,19 @@ Long64_t AliESDtrackCuts::Merge(TCollection* list) {
   return count+1;
 }
 
+void AliESDtrackCuts::SetMinNClustersTPCPtDep(TFormula *f1, Float_t ptmax) 
+{
+  //
+  // Sets the pT dependent NClustersTPC cut
+  //
+
+  if(f1){ 
+    delete f1CutMinNClustersTPCPtDep;
+    f1CutMinNClustersTPCPtDep = (TFormula*)f1->Clone("f1CutMinNClustersTPCPtDep"); 
+  }
+  fCutMaxPtDepNClustersTPC=ptmax; 
+}
+
 //____________________________________________________________________
 AliESDtrackCuts* AliESDtrackCuts::GetStandardTPCOnlyTrackCuts()
 {
@@ -689,12 +753,58 @@ AliESDtrackCuts* AliESDtrackCuts::GetStandardITSTPCTrackCuts2009(Bool_t selPrima
   if(selPrimaries) {
     // 7*(0.0050+0.0060/pt^0.9)
     esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0350+0.0420/pt^0.9");
+    esdTrackCuts->SetMaxChi2TPCConstrainedGlobal(36);
   }
   esdTrackCuts->SetMaxDCAToVertexZ(1.e6);
   esdTrackCuts->SetDCAToVertex2D(kFALSE);
   esdTrackCuts->SetRequireSigmaToVertex(kFALSE);
   //esdTrackCuts->SetEtaRange(-0.8,+0.8);
   
+  esdTrackCuts->SetMaxChi2PerClusterITS(36);
+  
+  return esdTrackCuts;
+}
+
+//____________________________________________________________________
+AliESDtrackCuts* AliESDtrackCuts::GetStandardITSTPCTrackCuts2011(Bool_t selPrimaries, Int_t clusterCut)
+{
+  // creates an AliESDtrackCuts object and fills it with standard values for ITS-TPC cuts for pp 2011 data  
+  // if clusterCut = 1, the cut on the number of clusters is replaced by
+  // a cut on the number of crossed rows and on the ration crossed
+  // rows/findable clusters
+
+  AliInfoClass("Creating track cuts for ITS+TPC (2011 definition).");
+  
+  AliESDtrackCuts* esdTrackCuts = new AliESDtrackCuts;
+
+  // TPC  
+  if(clusterCut == 0)  esdTrackCuts->SetMinNClustersTPC(50);
+  else if (clusterCut == 1) {
+    esdTrackCuts->SetMinNCrossedRowsTPC(70);
+    esdTrackCuts->SetMinRatioCrossedRowsOverFindableClustersTPC(0.8);
+  }
+  else {
+    AliWarningClass(Form("Wrong value of the clusterCut parameter (%d), using cut on Nclusters",clusterCut));
+    esdTrackCuts->SetMinNClustersTPC(50);
+  }
+  esdTrackCuts->SetMaxChi2PerClusterTPC(4);
+  esdTrackCuts->SetAcceptKinkDaughters(kFALSE);
+  esdTrackCuts->SetRequireTPCRefit(kTRUE);
+  // ITS
+  esdTrackCuts->SetRequireITSRefit(kTRUE);
+  esdTrackCuts->SetClusterRequirementITS(AliESDtrackCuts::kSPD,
+                                        AliESDtrackCuts::kAny);
+  if(selPrimaries) {
+    // 7*(0.0015+0.0050/pt^1.1)
+    esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0105+0.0350/pt^1.1");
+    esdTrackCuts->SetMaxChi2TPCConstrainedGlobal(36);
+  }
+  esdTrackCuts->SetMaxDCAToVertexZ(2);
+  esdTrackCuts->SetDCAToVertex2D(kFALSE);
+  esdTrackCuts->SetRequireSigmaToVertex(kFALSE);
+  
+  esdTrackCuts->SetMaxChi2PerClusterITS(36);
+
   return esdTrackCuts;
 }
 
@@ -730,18 +840,17 @@ AliESDtrackCuts* AliESDtrackCuts::GetStandardITSTPCTrackCuts2010(Bool_t selPrima
   if(selPrimaries) {
     // 7*(0.0026+0.0050/pt^1.01)
     esdTrackCuts->SetMaxDCAToVertexXYPtDep("0.0182+0.0350/pt^1.01");
+    esdTrackCuts->SetMaxChi2TPCConstrainedGlobal(36);
   }
   esdTrackCuts->SetMaxDCAToVertexZ(2);
   esdTrackCuts->SetDCAToVertex2D(kFALSE);
   esdTrackCuts->SetRequireSigmaToVertex(kFALSE);
   
+  esdTrackCuts->SetMaxChi2PerClusterITS(36);
+
   return esdTrackCuts;
 }
 
-//____________________________________________________________________
-
-
-
 //____________________________________________________________________
 AliESDtrackCuts* AliESDtrackCuts::GetStandardITSPureSATrackCuts2009(Bool_t selPrimaries, Bool_t useForPid)
 {
@@ -887,7 +996,7 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, Bool_t t
 }
 
 //____________________________________________________________________
-Float_t AliESDtrackCuts::GetSigmaToVertex(AliESDtrack* const esdTrack)
+Float_t AliESDtrackCuts::GetSigmaToVertex(const AliESDtrack* const esdTrack)
 {
   // Calculates the number of sigma to the vertex.
 
@@ -950,7 +1059,7 @@ void AliESDtrackCuts::EnableNeededBranches(TTree* tree)
 }
 
 //____________________________________________________________________
-Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack) 
+Bool_t AliESDtrackCuts::AcceptTrack(const AliESDtrack* esdTrack) 
 {
   // 
   // figure out if the tracks survives all the track cuts defined
@@ -975,6 +1084,8 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
   // fTracks.fR   //GetMass
   // fTracks.fP   //GetMass
   // fTracks.fKinkIndexes
+  //
+  // esdEvent is only required for the MaxChi2TPCConstrainedVsGlobal
 
   UInt_t status = esdTrack->GetStatus();
 
@@ -987,7 +1098,16 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
   else {
     nClustersTPC = esdTrack->GetTPCclusters(0);
   }
-  Float_t nCrossedRowsTPC = esdTrack->GetTPCClusterInfo(2,1); 
+  
+  //Pt dependent NClusters Cut
+  if(f1CutMinNClustersTPCPtDep) {
+    if(esdTrack->Pt()<fCutMaxPtDepNClustersTPC)
+      fCutMinNClusterTPC = (Int_t)(f1CutMinNClustersTPCPtDep->Eval(esdTrack->Pt()));
+    else
+      fCutMinNClusterTPC = (Int_t)(f1CutMinNClustersTPCPtDep->Eval(fCutMaxPtDepNClustersTPC));
+  }
+
+  Float_t nCrossedRowsTPC = esdTrack->GetTPCCrossedRows();
   Float_t  ratioCrossedRowsOverFindableClustersTPC = 1.0;
   if (esdTrack->GetTPCNclsF()>0) {
     ratioCrossedRowsOverFindableClustersTPC = nCrossedRowsTPC / esdTrack->GetTPCNclsF();
@@ -1012,9 +1132,6 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
   Double_t extCov[15];
   esdTrack->GetExternalCovariance(extCov);
 
-  // getting the track to vertex parameters
-  Float_t nSigmaToVertex = GetSigmaToVertex(esdTrack);
-      
   Float_t b[2];
   Float_t bCov[3];
   esdTrack->GetImpactParameters(b,bCov);
@@ -1045,9 +1162,12 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
   Double_t p[3];
   esdTrack->GetPxPyPz(p);
 
-  Float_t momentum = TMath::Sqrt(TMath::Power(p[0],2) + TMath::Power(p[1],2) + TMath::Power(p[2],2));
-  Float_t pt       = TMath::Sqrt(TMath::Power(p[0],2) + TMath::Power(p[1],2));
-  Float_t energy   = TMath::Sqrt(TMath::Power(esdTrack->GetMass(),2) + TMath::Power(momentum,2));
+  // Changed from float to double to prevent rounding errors leading to negative 
+  // log arguments (M.G.)
+  Double_t momentum = TMath::Sqrt(p[0]*p[0] + p[1]*p[1] + p[2]*p[2]);
+  Double_t pt       = TMath::Sqrt(p[0]*p[0] + p[1]*p[1]);
+  Double_t mass     = esdTrack->GetMass();
+  Double_t energy   = TMath::Sqrt(mass*mass + momentum*momentum);
 
   //y-eta related calculations
   Float_t eta = -100.;
@@ -1095,11 +1215,9 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
     cuts[10]=kTRUE;  
   if (extCov[14]  > fCutMaxC55) 
     cuts[11]=kTRUE;  
-  if (nSigmaToVertex > fCutNsigmaToVertex && fCutSigmaToVertexRequired)
-    cuts[12] = kTRUE;
-  // if n sigma could not be calculated
-  if (nSigmaToVertex<0 && fCutSigmaToVertexRequired)
-    cuts[13]=kTRUE;
+  
+  // cut 12 and 13 see below
+  
   if (!fCutAcceptKinkDaughters && esdTrack->GetKinkIndex(0)>0)
     cuts[14]=kTRUE;
   // track kinematics cut
@@ -1130,8 +1248,18 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
   if (!fCutDCAToVertex2D && TMath::Abs(dcaToVertexZ) < fCutMinDCAToVertexZ)
     cuts[27] = kTRUE;
   
-  for (Int_t i = 0; i < 3; i++)
-    cuts[28+i] = !CheckITSClusterRequirement(fCutClusterRequirementITS[i], esdTrack->HasPointOnITSLayer(i*2), esdTrack->HasPointOnITSLayer(i*2+1));
+  for (Int_t i = 0; i < 3; i++) {
+    if(!(esdTrack->GetStatus()&AliESDtrack::kITSupg)) { // current ITS
+      cuts[28+i] = !CheckITSClusterRequirement(fCutClusterRequirementITS[i], esdTrack->HasPointOnITSLayer(i*2), esdTrack->HasPointOnITSLayer(i*2+1));
+    } else { // upgraded ITS (7 layers)
+      // at the moment, for L012 the layers 12 are considered together
+      if(i==0) { // L012
+       cuts[28+i] = !CheckITSClusterRequirement(fCutClusterRequirementITS[i], esdTrack->HasPointOnITSLayer(0), (esdTrack->HasPointOnITSLayer(1))&(esdTrack->HasPointOnITSLayer(2)));
+      } else { // L34 or L56
+       cuts[28+i] = !CheckITSClusterRequirement(fCutClusterRequirementITS[i], esdTrack->HasPointOnITSLayer(i*2+1), esdTrack->HasPointOnITSLayer(i*2+2));
+      }
+    }
+  }
   
   if(fCutRequireITSStandAlone || fCutRequireITSpureSA){
     if ((status & AliESDtrack::kITSin) == 0 || (status & AliESDtrack::kTPCin)){
@@ -1177,11 +1305,112 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
     if(retc && statusLay==5) ++nMissITSpts;
   }
   if(nMissITSpts>fCutMaxMissingITSPoints) cuts[38] = kTRUE;
-
+  
+  //kTOFout
+  if (fCutRequireTOFout && (status&AliESDtrack::kTOFout)==0)
+    cuts[40]=kTRUE;
+
+  // TOF signal Dz cut
+  Float_t dxTOF = esdTrack->GetTOFsignalDx();
+  Float_t dzTOF = esdTrack->GetTOFsignalDz();
+  if (fFlagCutTOFdistance && (esdTrack->GetStatus() & AliESDtrack::kTOFout) == AliESDtrack::kTOFout){ // applying the TOF distance cut only if requested, and only on tracks that reached the TOF and where associated with a TOF hit 
+         if (fgBeamTypeFlag < 0) {  // the check on the beam type was not done yet
+                 const AliESDEvent* event = esdTrack->GetESDEvent();
+                 if (event){
+                         TString beamTypeESD = event->GetBeamType();
+                         AliDebug(2,Form("Beam type from ESD event = %s",beamTypeESD.Data()));
+                         if (beamTypeESD.CompareTo("A-A",TString::kIgnoreCase) == 0){ // we are in PbPb collisions --> fgBeamTypeFlag will be set to 1, to apply the cut on TOF signal Dz
+                                 fgBeamTypeFlag = 1;
+                         }
+                         else { // we are NOT in PbPb collisions --> fgBeamTypeFlag will be set to 0, to NOT apply the cu6 on TOF signal Dz
+                                 fgBeamTypeFlag = 0;
+                         }                               
+                 }
+                 else{
+                         AliFatal("Beam type not available, but it is needed to apply the TOF cut!");
+                 }
+         }
+
+         if (fgBeamTypeFlag == 1){ // we are in PbPb collisions --> apply the cut on TOF signal Dz
+                 Float_t radiusTOF = TMath::Sqrt(dxTOF*dxTOF + dzTOF*dzTOF);
+                 AliDebug(3,Form("TOF check (with fCutTOFdistance = %f) --> dx = %f, dz = %f, radius = %f", fCutTOFdistance, dxTOF, dzTOF, radiusTOF));
+                 if (radiusTOF > fCutTOFdistance){
+                         AliDebug(2, Form("************* the radius is outside the range! %f > %f, the track will be skipped", radiusTOF, fCutTOFdistance));
+                         cuts[41] = kTRUE;
+                 }
+         }
+  }
+  
   Bool_t cut=kFALSE;
   for (Int_t i=0; i<kNCuts; i++) 
     if (cuts[i]) {cut = kTRUE;}
 
+  // for performance evaluate the CPU intensive cuts only when the others have passed, and when they are requested
+  Double_t chi2TPCConstrainedVsGlobal = -2;
+  Float_t nSigmaToVertex = -2;
+  if (!cut)
+  {
+    // getting the track to vertex parameters
+    if (fCutSigmaToVertexRequired)
+    {
+      nSigmaToVertex = GetSigmaToVertex(esdTrack);
+      if (nSigmaToVertex > fCutNsigmaToVertex && fCutSigmaToVertexRequired)
+      {
+       cuts[12] = kTRUE;
+       cut = kTRUE;
+      }
+      // if n sigma could not be calculated
+      if (nSigmaToVertex<0 && fCutSigmaToVertexRequired)
+      {
+       cuts[13] = kTRUE;
+       cut = kTRUE;
+      }
+    }
+      
+    // max chi2 TPC constrained vs global track only if track passed the other cut
+    if (fCutMaxChi2TPCConstrainedVsGlobal < 1e9)
+    {
+      const AliESDEvent* esdEvent = esdTrack->GetESDEvent();
+      
+      if (!esdEvent)
+       AliFatal("fCutMaxChi2TPCConstrainedVsGlobal set but ESD event not set in AliESDTrack. Use AliESDTrack::SetESDEvent before calling AliESDtrackCuts.");
+      
+      // get vertex
+      const AliESDVertex* vertex = 0;
+      if (fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexTracks)
+       vertex = esdEvent->GetPrimaryVertexTracks();
+      
+      if ((!vertex || !vertex->GetStatus()) && fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexSPD)
+       vertex = esdEvent->GetPrimaryVertexSPD();
+       
+      if ((!vertex || !vertex->GetStatus()) && fCutMaxChi2TPCConstrainedVsGlobalVertexType & kVertexTPC)
+       vertex = esdEvent->GetPrimaryVertexTPC();
+
+      if (vertex->GetStatus())
+       chi2TPCConstrainedVsGlobal = esdTrack->GetChi2TPCConstrainedVsGlobal(vertex);
+      
+      if (chi2TPCConstrainedVsGlobal < 0 || chi2TPCConstrainedVsGlobal > fCutMaxChi2TPCConstrainedVsGlobal)
+      {
+       cuts[39] = kTRUE;
+       cut = kTRUE;
+      }
+    }
+
+    // max length in active volume
+    Float_t lengthInActiveZoneTPC = -1;
+    if (fCutMinLengthActiveVolumeTPC > 1.) { // do the calculation only if needed to save cpu-time
+      if (esdTrack->GetESDEvent()) {
+       if (esdTrack->GetInnerParam()) lengthInActiveZoneTPC = esdTrack->GetLengthInActiveZone(1, 1.8, 220, esdTrack->GetESDEvent()->GetMagneticField()); 
+       //
+       if (lengthInActiveZoneTPC < fCutMinLengthActiveVolumeTPC ) {
+         cuts[42] = kTRUE;
+         cut = kTRUE;
+       }
+      }
+    }
+
+    
+  }
 
   //########################################################################
   // filling histograms
@@ -1224,6 +1453,7 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
       fhRatioCrossedRowsOverFindableClustersTPC[id]->Fill(ratioCrossedRowsOverFindableClustersTPC);
       fhChi2PerClusterITS[id]->Fill(chi2PerClusterITS);
       fhChi2PerClusterTPC[id]->Fill(chi2PerClusterTPC);
+      fhChi2TPCConstrainedVsGlobal[id]->Fill(chi2TPCConstrainedVsGlobal);
       fhNClustersForITSPID[id]->Fill(nITSPointsForPid);
       fhNMissingITSPoints[id]->Fill(nMissITSpts);
 
@@ -1237,6 +1467,7 @@ Bool_t AliESDtrackCuts::AcceptTrack(AliESDtrack* esdTrack)
 
       fhPt[id]->Fill(pt);
       fhEta[id]->Fill(eta);
+      fhTOFdistance[id]->Fill(dxTOF, dzTOF);
 
       Float_t bRes[2];
       bRes[0] = TMath::Sqrt(bCov[0]);
@@ -1284,11 +1515,9 @@ Bool_t AliESDtrackCuts::CheckITSClusterRequirement(ITSClusterRequirement req, Bo
 }
 
 //____________________________________________________________________
-AliESDtrack* AliESDtrackCuts::GetTPCOnlyTrack(AliESDEvent* esd, Int_t iTrack)
+AliESDtrack* AliESDtrackCuts::GetTPCOnlyTrack(const AliESDEvent* esd, Int_t iTrack)
 {
-  
-  // Utility function to 
-  // create a TPC only track from the given esd track
+  // Utility function to create a TPC only track from the given esd track
   // 
   // IMPORTANT: The track has to be deleted by the user
   //
@@ -1317,16 +1546,11 @@ AliESDtrack* AliESDtrackCuts::GetTPCOnlyTrack(AliESDEvent* esd, Int_t iTrack)
     return 0;
   }
 
-  // propagate to Vertex
-  // not needed for normal reconstructed ESDs...
-  // Double_t pTPC[2],covTPC[3];
-  // tpcTrack->PropagateToDCA(esd->GetPrimaryVertexTPC(), esd->GetMagneticField(), 10000,  pTPC, covTPC);
-
   return tpcTrack;
 }
 
 //____________________________________________________________________
-TObjArray* AliESDtrackCuts::GetAcceptedTracks(AliESDEvent* esd,Bool_t bTPC)
+TObjArray* AliESDtrackCuts::GetAcceptedTracks(const AliESDEvent* esd, Bool_t bTPC)
 {
   //
   // returns an array of all tracks that pass the cuts
@@ -1423,6 +1647,7 @@ Int_t AliESDtrackCuts::CountAcceptedTracks(const AliESDEvent* const esd)
     fhRatioCrossedRowsOverFindableClustersTPC[i]     = new TH1F("ratioCrossedRowsOverFindableClustersTPC"  ,"",60,0,1.5);
     fhChi2PerClusterITS[i]   = new TH1F("chi2PerClusterITS","",500,0,10);
     fhChi2PerClusterTPC[i]   = new TH1F("chi2PerClusterTPC","",500,0,10);
+    fhChi2TPCConstrainedVsGlobal[i]   = new TH1F("chi2TPCConstrainedVsGlobal","",600,-2,50);
     fhNClustersForITSPID[i]  = new TH1F("nPointsForITSpid","",5,-0.5,4.5);
     fhNMissingITSPoints[i]   = new TH1F("nMissingITSClusters","",7,-0.5,6.5);
 
@@ -1447,12 +1672,14 @@ Int_t AliESDtrackCuts::CountAcceptedTracks(const AliESDEvent* const esd)
 
     fhPt[i]                  = new TH1F("pt"     ,"p_{T} distribution;p_{T} (GeV/c)", 800, 0.0, 10.0);
     fhEta[i]                 = new TH1F("eta"     ,"#eta distribution;#eta",40,-2.0,2.0);
+    fhTOFdistance[i]         = new TH2F("TOFdistance"     ,"TOF distance;dx (cm};dz (cm)", 150, -15, 15, 150, -15, 15);
     
     fhNClustersITS[i]->SetTitle("n ITS clusters");
     fhNClustersTPC[i]->SetTitle("n TPC clusters");
     fhNSharedClustersTPC[i]->SetTitle("n TPC shared clusters");
     fhChi2PerClusterITS[i]->SetTitle("#Chi^{2} per ITS cluster");
     fhChi2PerClusterTPC[i]->SetTitle("#Chi^{2} per TPC cluster");
+    fhChi2TPCConstrainedVsGlobal[i]->SetTitle("#Chi^{2} TPC constrained track vs global track");
     fhNClustersForITSPID[i]->SetTitle("n ITS points for PID");
     fhNMissingITSPoints[i]->SetTitle("n ITS layers with missing cluster");
 
@@ -1481,6 +1708,7 @@ Int_t AliESDtrackCuts::CountAcceptedTracks(const AliESDEvent* const esd)
     fhNSharedClustersTPC[i]->SetLineColor(color);  fhNSharedClustersTPC[i]->SetLineWidth(2);
     fhChi2PerClusterITS[i]->SetLineColor(color);   fhChi2PerClusterITS[i]->SetLineWidth(2);
     fhChi2PerClusterTPC[i]->SetLineColor(color);   fhChi2PerClusterTPC[i]->SetLineWidth(2);
+    fhChi2TPCConstrainedVsGlobal[i]->SetLineColor(color);   fhChi2TPCConstrainedVsGlobal[i]->SetLineWidth(2);
     fhNClustersForITSPID[i]->SetLineColor(color);  fhNClustersForITSPID[i]->SetLineWidth(2);
     fhNMissingITSPoints[i]->SetLineColor(color);   fhNMissingITSPoints[i]->SetLineWidth(2);
 
@@ -1542,6 +1770,7 @@ Bool_t AliESDtrackCuts::LoadHistograms(const Char_t* dir)
     fhRatioCrossedRowsOverFindableClustersTPC[i]   = dynamic_cast<TH1F*> (gDirectory->Get("ratioCrossedRowsOverFindableClustersTPC"  ));
     fhChi2PerClusterITS[i] = dynamic_cast<TH1F*> (gDirectory->Get("chi2PerClusterITS"));
     fhChi2PerClusterTPC[i] = dynamic_cast<TH1F*> (gDirectory->Get("chi2PerClusterTPC"));
+    fhChi2TPCConstrainedVsGlobal[i] = dynamic_cast<TH1F*> (gDirectory->Get("fhChi2TPCConstrainedVsGlobal"));
     fhNClustersForITSPID[i] = dynamic_cast<TH1F*> (gDirectory->Get("nPointsForITSpid"));
     fhNMissingITSPoints[i] = dynamic_cast<TH1F*> (gDirectory->Get("nMissingITSClusters"));
 
@@ -1565,6 +1794,7 @@ Bool_t AliESDtrackCuts::LoadHistograms(const Char_t* dir)
 
     fhPt[i] = dynamic_cast<TH1F*> (gDirectory->Get("pt"));
     fhEta[i] = dynamic_cast<TH1F*> (gDirectory->Get("eta"));
+    fhTOFdistance[i] = dynamic_cast<TH2F*> (gDirectory->Get("TOFdistance"));
 
     gDirectory->cd("../");
   }
@@ -1614,6 +1844,7 @@ void AliESDtrackCuts::SaveHistograms(const Char_t* dir) {
     fhRatioCrossedRowsOverFindableClustersTPC[i]     ->Write();
     fhChi2PerClusterITS[i]   ->Write();
     fhChi2PerClusterTPC[i]   ->Write();
+    fhChi2TPCConstrainedVsGlobal[i]   ->Write();
     fhNClustersForITSPID[i]  ->Write();
     fhNMissingITSPoints[i]   ->Write();
 
@@ -1637,6 +1868,7 @@ void AliESDtrackCuts::SaveHistograms(const Char_t* dir) {
 
     fhPt[i]                  ->Write();
     fhEta[i]                 ->Write();
+    fhTOFdistance[i]         ->Write();
     
     gDirectory->cd("../");
   }
@@ -2011,24 +2243,24 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
   Int_t trackletsITSSA_complementary = 0; //number of SPD tracklets complementary to ITSSA tracks for a given event
 
   const Int_t nESDTracks = esd->GetNumberOfTracks();
-  Int_t highestID = 0;
 
   // flags for secondary and rejected tracks
   const Int_t kRejBit = BIT(15); // set this bit in global tracks if it is rejected by a cut
   const Int_t kSecBit = BIT(16); // set this bit in global tracks if it is secondary according to a cut
   
   for(Int_t itracks=0; itracks < nESDTracks; itracks++) {
-    if(esd->GetTrack(itracks)->GetLabel() > highestID) highestID = esd->GetTrack(itracks)->GetLabel();
     esd->GetTrack(itracks)->ResetBit(kSecBit|kRejBit); //reset bits used for flagging secondaries and rejected tracks in case they were changed before this analysis
   }
-  const Int_t maxid = highestID+1; // used to define bool array for check multiple associations of tracklets to one track. array starts at 0.
+  const Int_t maxid = nESDTracks; // used to define bool array for check multiple associations of tracklets to one track. array starts at 0.
   
   // bit mask for esd tracks, to check if multiple tracklets are associated to it
-  Bool_t globalBits[maxid], pureITSBits[maxid];
-  for(Int_t i=0; i<maxid; i++){ // set all bools to false
-      globalBits[i]=kFALSE;
-      pureITSBits[i]=kFALSE;
-  }
+  TBits globalBits(maxid), pureITSBits(maxid);
+  // why labels are used with the data? RS
+  //  Bool_t globalBits[maxid], pureITSBits[maxid];
+  //  for(Int_t i=0; i<maxid; i++){ // set all bools to false
+  //      globalBits[i]=kFALSE;
+  //      pureITSBits[i]=kFALSE;
+  //  }
 
   //*******************************************************************************************************
   // get multiplicity from global tracks
@@ -2040,13 +2272,13 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
       track->SetBit(kSecBit);
       continue;
     }
-    
+    /* done via proper DCA cut
     //secondary?
     if (track->IsOn(AliESDtrack::kMultSec)) {
       track->SetBit(kSecBit);
       continue;
     }
-
+    */
     // check tracks with ITS part
     //*******************************************************************************************************
     if (track->IsOn(AliESDtrack::kITSin) && !track->IsOn(AliESDtrack::kITSpureSA) && trackType == kTrackletsITSTPC) { // track has ITS part but is not an ITS_SA
@@ -2056,7 +2288,7 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
           if (fgMultEstTrackCuts[kMultEstTrackCutGlobal]->AcceptTrack(track)) { // good ITSTPC track
             if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
               tracksITSTPC++; //global track counted
-              globalBits[itracks] = kTRUE;
+              globalBits.SetBitNumber(itracks);
             }
             else track->SetBit(kSecBit); // large DCA -> secondary, don't count either track not associated tracklet
           }
@@ -2067,7 +2299,7 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
       else if (fgMultEstTrackCuts[kMultEstTrackCutITSSA]->AcceptTrack(track)) { // good ITS complementary track
         if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
           tracksITSTPCSA_complementary++;
-          globalBits[itracks] = kTRUE;
+          globalBits.SetBitNumber(itracks);
         }
         else track->SetBit(kSecBit); // large DCA -> secondary, don't count either track not associated tracklet
       }
@@ -2079,9 +2311,9 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
       if (fgMultEstTrackCuts[kMultEstTrackCutITSSA]->AcceptTrack(track)) { // good ITSSA track
         if (fgMultEstTrackCuts[kMultEstTrackCutDCAwSPD]->AcceptTrack(track) || fgMultEstTrackCuts[kMultEstTrackCutDCAwoSPD]->AcceptTrack(track)) {
           tracksITSSA++;
-          pureITSBits[itracks] = kTRUE;
+          pureITSBits.SetBitNumber(itracks);
         }
-        else track->SetBit(kRejBit);
+        else track->SetBit(kSecBit);
       }
       else track->SetBit(kRejBit);
     }
@@ -2094,42 +2326,50 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
     if (TMath::Abs(spdmult->GetEta(i)) > etaRange) continue; // eta selection for tracklets
     
     // if counting tracks+tracklets, check if clusters were already used in tracks
-    Int_t id1,id2,id3,id4;
-    spdmult->GetTrackletTrackIDs(i,0,id1,id2); // references for eventual Global/ITS_SA tracks
-    AliESDtrack* tr1 = id1>=0 ? esd->GetTrack(id1) : 0;
-    spdmult->GetTrackletTrackIDs(i,1,id3,id4); // references for eventual ITS_SA_pure tracks
-    AliESDtrack* tr3 = id3>=0 ? esd->GetTrack(id3) : 0;
-
+    Int_t id1, id2, id3, id4;
+    spdmult->GetTrackletTrackIDs ( i, 0, id1, id2 ); // references for eventual Global/ITS_SA tracks
+    spdmult->GetTrackletTrackIDs ( i, 1, id3, id4 ); // references for eventual ITS_SA_pure tracks
+    
     // are both clusters from the same tracks? If not, skip the tracklet (shouldn't change things much)
-    if ((id1!=id2 && id1>=0 && id2>=0) || (id3!=id4 && id3>=0 && id4>=0)) continue;
-
-    Bool_t bUsedInGlobal = (id1 != -1) ? globalBits[id1] : 0;// has associated global track been associated to a previous tracklet?
-    Bool_t bUsedInPureITS = (id3 != -1) ? pureITSBits[id3] : 0;// has associated pure ITS track been associated to a previous tracklet?
+    if ( ( id1 != id2 && id1 >= 0 && id2 >= 0 ) || ( id3 != id4 && id3 >= 0 && id4 >= 0 ) ) continue;
+    
+    //referenced track
+    //at this point we either have id1 = id2 (id3 = id4) or only one of the ids pair is -1
+    // id1>=0, id2>=0, id1=id2 : tracklet has associated track
+    // id1>=0, id2 = -1                : 1st layer cluster has associated track
+    // id1=-1, id2>=0          : 2nd layer cluster has associated track
+    // id1=-1, id2=-1          : tracklet has no associated track
+    //
+    Int_t bUsedInGlobal(-1);
+    if ( id1 != -1 ) bUsedInGlobal = globalBits.TestBitNumber(id1) ? id1 : -1;
+    else if ( id2 != -1) bUsedInGlobal = globalBits.TestBitNumber(id2) ? id2 : -1;
+    Int_t bUsedInPureITS(-1);
+    if ( id3 != -1 ) bUsedInPureITS = pureITSBits.TestBitNumber(id3) ? id3 : -1;
+    else if ( id4 != -1) bUsedInPureITS = pureITSBits.TestBitNumber(id4) ? id4 : -1;
+    //
+    AliESDtrack* tr_global = bUsedInGlobal >= 0 ? esd->GetTrack ( bUsedInGlobal ) : 0;
+    AliESDtrack* tr_itssa = bUsedInPureITS >= 0 ? esd->GetTrack ( bUsedInPureITS ) : 0;
+    //
+    // has associated pure ITS track been associated to a previous tracklet?
     //*******************************************************************************************************
     if (trackType == kTrackletsITSTPC) {
-      // count tracklets towards global+complementary tracks
-      if (  (tr1 && !tr1->TestBit(kSecBit)) &&   // reject as secondary
-        (tr1 &&  tr1->TestBit(kRejBit)) ) {  // count tracklet as bad quality track
-          if(!bUsedInGlobal){
-            ++trackletsITSTPC_complementary;
-            if(id1>0) globalBits[id1] = kTRUE; // mark global track linked to this tracklet as "associated"
-          }
-      }
-      else if(id1<0) {
-        ++trackletsITSTPC_complementary; // if no associated track, count the tracklet
-      }
+           //*******************************************************************************************************
+           // count tracklets towards global+complimentary tracks
+           if ( ( tr_global && !tr_global->TestBit ( kSecBit ) ) && ( tr_global &&  tr_global->TestBit ( kRejBit ) ) ) {  // count tracklet as bad quality track
+                   globalBits.SetBitNumber( bUsedInGlobal ); // mark global track linked to this tracklet as used
+                   ++trackletsITSTPC_complementary;
+           } 
+           
+           if ( bUsedInGlobal < 0 ) ++trackletsITSTPC_complementary; //no associated track, just count the tracklet
     } else {
-      // count tracklets towards ITS_SA_pure tracks
-      if (  (tr3 && !tr3->TestBit(kSecBit)) &&   // reject as secondary
-        (tr3 &&  tr3->TestBit(kRejBit)) ) { // count tracklet as bad quality track
-        if(!bUsedInPureITS) {
-          ++trackletsITSSA_complementary;
-          if(id3>0) pureITSBits[id3] = kTRUE; // mark global track linked to this tracklet as "associated"
-        }
-      }
-      else if(id3<0) {
-        ++trackletsITSSA_complementary; // if no associated track, count the tracklet
-      }
+           //*******************************************************************************************************
+           // count tracklets towards ITS_SA_pure tracks
+           if ( ( tr_itssa && !tr_itssa->TestBit ( kSecBit ) ) && ( tr_itssa &&  tr_itssa->TestBit ( kRejBit ) ) ) {  // count tracklet as bad quality track
+                   pureITSBits.SetBitNumber( bUsedInPureITS ); // mark ITS pure SA track linked to this tracklet as used
+                   ++trackletsITSSA_complementary;
+           } 
+           
+           if ( bUsedInPureITS < 0 ) ++trackletsITSSA_complementary; //no associated track, just count the tracklet
     }
   }
   
@@ -2141,3 +2381,15 @@ Int_t AliESDtrackCuts::GetReferenceMultiplicity(const AliESDEvent* esd, MultEstT
 
   return multiplicityEstimate;
 }
+
+//____________________________________________________________________
+void AliESDtrackCuts::SetRequireStandardTOFmatchCuts(){
+
+       // setting the TOF cuts flags (kTOFout = TOF matching distance) to true, to include the selection on the standard TOF matching 
+
+       SetRequireTOFout(kTRUE);
+       SetFlagCutTOFdistance(kTRUE);
+       SetCutTOFdistance(3.);
+
+}
+