1 /**************************************************************************
\r
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
\r
4 * Author: The ALICE Off-line Project. *
\r
5 * Contributors are mentioned in the code where appropriate. *
\r
7 * Permission to use, copy, modify and distribute this software and its *
\r
8 * documentation strictly for non-commercial purposes is hereby granted *
\r
9 * without fee, provided that the above copyright notice appears in all *
\r
10 * copies and that both the copyright notice and this permission notice *
\r
11 * appear in the supporting documentation. The authors make no claims *
\r
12 * about the suitability of this software for any purpose. It is *
\r
13 * provided "as is" without express or implied warranty. *
\r
14 **************************************************************************/
\r
21 #include <TArrayI.h>
\r
22 #include <TRandom.h>
\r
23 #include <TParticle.h>
\r
26 #include "AliAnalysisTaskESDfilter.h"
\r
27 #include "AliAnalysisManager.h"
\r
28 #include "AliESDEvent.h"
\r
29 #include "AliESDRun.h"
\r
30 #include "AliStack.h"
\r
31 #include "AliAODEvent.h"
\r
32 #include "AliMCEvent.h"
\r
33 #include "AliMCEventHandler.h"
\r
34 #include "AliESDInputHandler.h"
\r
35 #include "AliAODHandler.h"
\r
36 #include "AliAODMCParticle.h"
\r
37 #include "AliAnalysisFilter.h"
\r
38 #include "AliESDMuonTrack.h"
\r
39 #include "AliESDVertex.h"
\r
40 #include "AliCentrality.h"
\r
41 #include "AliEventplane.h"
\r
42 #include "AliESDv0.h"
\r
43 #include "AliESDkink.h"
\r
44 #include "AliESDcascade.h"
\r
45 #include "AliESDPmdTrack.h"
\r
46 #include "AliESDCaloCluster.h"
\r
47 #include "AliESDCaloCells.h"
\r
48 #include "AliMultiplicity.h"
\r
50 #include "AliCodeTimer.h"
\r
51 #include "AliESDtrackCuts.h"
\r
52 #include "AliESDpid.h"
\r
53 #include "Riostream.h"
\r
55 ClassImp(AliAnalysisTaskESDfilter)
\r
57 ////////////////////////////////////////////////////////////////////////
\r
59 AliAnalysisTaskESDfilter::AliAnalysisTaskESDfilter():
\r
60 AliAnalysisTaskSE(),
\r
64 fCascadeFilter(0x0),
\r
67 fEnableFillAOD(kTRUE),
\r
76 fNumberOfPositiveTracks(0),
\r
78 fNumberOfVertices(0),
\r
79 fNumberOfCascades(0),
\r
81 fOldESDformat(kFALSE),
\r
82 fPrimaryVertex(0x0),
\r
83 fTPCConstrainedFilterMask(0),
\r
84 fHybridFilterMaskTPCCG(0),
\r
85 fWriteHybridTPCCOnly(kFALSE),
\r
86 fGlobalConstrainedFilterMask(0),
\r
87 fHybridFilterMaskGCG(0),
\r
88 fWriteHybridGCOnly(kFALSE),
\r
89 fIsVZEROEnabled(kTRUE),
\r
90 fIsZDCEnabled(kTRUE),
\r
91 fAreCascadesEnabled(kTRUE),
\r
92 fAreV0sEnabled(kTRUE),
\r
93 fAreKinksEnabled(kTRUE),
\r
94 fAreTracksEnabled(kTRUE),
\r
95 fArePmdClustersEnabled(kTRUE),
\r
96 fAreCaloClustersEnabled(kTRUE),
\r
97 fAreEMCALCellsEnabled(kTRUE),
\r
98 fArePHOSCellsEnabled(kTRUE),
\r
99 fAreTrackletsEnabled(kTRUE),
\r
101 fIsPidOwner(kFALSE),
\r
102 fTimeZeroType(AliESDpid::kTOF_T0),
\r
103 fTPCaloneTrackCuts(0)
\r
105 // Default constructor
\r
108 //______________________________________________________________________________
\r
109 AliAnalysisTaskESDfilter::AliAnalysisTaskESDfilter(const char* name):
\r
110 AliAnalysisTaskSE(name),
\r
114 fCascadeFilter(0x0),
\r
115 fHighPthreshold(0),
\r
117 fEnableFillAOD(kTRUE),
\r
121 fAODTrackRefs(0x0),
\r
122 fAODV0VtxRefs(0x0),
\r
125 fNumberOfTracks(0),
\r
126 fNumberOfPositiveTracks(0),
\r
128 fNumberOfVertices(0),
\r
129 fNumberOfCascades(0),
\r
131 fOldESDformat(kFALSE),
\r
132 fPrimaryVertex(0x0),
\r
133 fTPCConstrainedFilterMask(0),
\r
134 fHybridFilterMaskTPCCG(0),
\r
135 fWriteHybridTPCCOnly(kFALSE),
\r
136 fGlobalConstrainedFilterMask(0),
\r
137 fHybridFilterMaskGCG(0),
\r
138 fWriteHybridGCOnly(kFALSE),
\r
139 fIsVZEROEnabled(kTRUE),
\r
140 fIsZDCEnabled(kTRUE),
\r
141 fAreCascadesEnabled(kTRUE),
\r
142 fAreV0sEnabled(kTRUE),
\r
143 fAreKinksEnabled(kTRUE),
\r
144 fAreTracksEnabled(kTRUE),
\r
145 fArePmdClustersEnabled(kTRUE),
\r
146 fAreCaloClustersEnabled(kTRUE),
\r
147 fAreEMCALCellsEnabled(kTRUE),
\r
148 fArePHOSCellsEnabled(kTRUE),
\r
149 fAreTrackletsEnabled(kTRUE),
\r
151 fIsPidOwner(kFALSE),
\r
152 fTimeZeroType(AliESDpid::kTOF_T0),
\r
153 fTPCaloneTrackCuts(0)
\r
157 AliAnalysisTaskESDfilter::~AliAnalysisTaskESDfilter(){
\r
158 if(fIsPidOwner) delete fESDpid;
\r
160 //______________________________________________________________________________
\r
161 void AliAnalysisTaskESDfilter::UserCreateOutputObjects()
\r
164 // Create Output Objects conenct filter to outputtree
\r
168 OutputTree()->GetUserInfo()->Add(fTrackFilter);
\r
172 AliError("No OutputTree() for adding the track filter");
\r
174 fTPCaloneTrackCuts = AliESDtrackCuts::GetStandardTPCOnlyTrackCuts();
\r
177 //______________________________________________________________________________
\r
178 void AliAnalysisTaskESDfilter::Init()
\r
181 if (fDebug > 1) AliInfo("Init() \n");
\r
182 // Call configuration file
\r
185 //______________________________________________________________________________
\r
186 void AliAnalysisTaskESDfilter::PrintTask(Option_t *option, Int_t indent) const
\r
190 AliAnalysisTaskSE::PrintTask(option,indent);
\r
192 TString spaces(' ',indent+3);
\r
194 cout << spaces.Data() << Form("Cascades are %s",fAreCascadesEnabled ? "ENABLED":"DISABLED") << endl;
\r
195 cout << spaces.Data() << Form("V0s are %s",fAreV0sEnabled ? "ENABLED":"DISABLED") << endl;
\r
196 cout << spaces.Data() << Form("Kinks are %s",fAreKinksEnabled ? "ENABLED":"DISABLED") << endl;
\r
197 cout << spaces.Data() << Form("Tracks are %s",fAreTracksEnabled ? "ENABLED":"DISABLED") << endl;
\r
198 cout << spaces.Data() << Form("PmdClusters are %s",fArePmdClustersEnabled ? "ENABLED":"DISABLED") << endl;
\r
199 cout << spaces.Data() << Form("CaloClusters are %s",fAreCaloClustersEnabled ? "ENABLED":"DISABLED") << endl;
\r
200 cout << spaces.Data() << Form("EMCAL cells are %s",fAreEMCALCellsEnabled ? "ENABLED":"DISABLED") << endl;
\r
201 cout << spaces.Data() << Form("Tracklets are %s",fAreTrackletsEnabled ? "ENABLED":"DISABLED") << endl;
\r
204 //______________________________________________________________________________
\r
205 void AliAnalysisTaskESDfilter::UserExec(Option_t */*option*/)
\r
207 // Execute analysis for current event
\r
210 Long64_t ientry = Entry();
\r
213 printf("Filter: Analysing event # %5d\n", (Int_t) ientry);
\r
214 if (fHighPthreshold == 0) AliInfo("detector PID signals are stored in each track");
\r
215 if (!fPtshape) AliInfo("detector PID signals are not stored below the pt threshold");
\r
217 // Filters must explicitely enable AOD filling in their UserExec (AG)
\r
218 if (!AliAnalysisManager::GetAnalysisManager()->GetOutputEventHandler()) AliFatal("Cannot run ESD filter without an output event handler");
\r
219 if(fEnableFillAOD) {
\r
220 AliAnalysisManager::GetAnalysisManager()->GetOutputEventHandler()->SetFillAOD(kTRUE);
\r
221 AliAnalysisManager::GetAnalysisManager()->GetOutputEventHandler()->SetFillExtension(kTRUE);
\r
226 //______________________________________________________________________________
\r
227 TClonesArray& AliAnalysisTaskESDfilter::Cascades()
\r
229 return *(AODEvent()->GetCascades());
\r
232 //______________________________________________________________________________
\r
233 TClonesArray& AliAnalysisTaskESDfilter::Tracks()
\r
235 return *(AODEvent()->GetTracks());
\r
238 //______________________________________________________________________________
\r
239 TClonesArray& AliAnalysisTaskESDfilter::V0s()
\r
241 return *(AODEvent()->GetV0s());
\r
244 //______________________________________________________________________________
\r
245 TClonesArray& AliAnalysisTaskESDfilter::Vertices()
\r
247 return *(AODEvent()->GetVertices());
\r
250 //______________________________________________________________________________
\r
251 AliAODHeader* AliAnalysisTaskESDfilter::ConvertHeader(const AliESDEvent& esd)
\r
253 AliCodeTimerAuto("",0);
\r
255 AliAODHeader* header = AODEvent()->GetHeader();
\r
257 header->SetRunNumber(esd.GetRunNumber());
\r
258 header->SetOfflineTrigger(fInputHandler->IsEventSelected()); // propagate the decision of the physics selection
\r
260 TTree* tree = fInputHandler->GetTree();
\r
262 TFile* file = tree->GetCurrentFile();
\r
263 if (file) header->SetESDFileName(file->GetName());
\r
266 if (fOldESDformat) {
\r
267 header->SetBunchCrossNumber(0);
\r
268 header->SetOrbitNumber(0);
\r
269 header->SetPeriodNumber(0);
\r
270 header->SetEventType(0);
\r
271 header->SetMuonMagFieldScale(-999.);
\r
272 header->SetCentrality(0);
\r
273 header->SetEventplane(0);
\r
275 header->SetBunchCrossNumber(esd.GetBunchCrossNumber());
\r
276 header->SetOrbitNumber(esd.GetOrbitNumber());
\r
277 header->SetPeriodNumber(esd.GetPeriodNumber());
\r
278 header->SetEventType(esd.GetEventType());
\r
280 header->SetEventNumberESDFile(esd.GetHeader()->GetEventNumberInFile());
\r
281 if(const_cast<AliESDEvent&>(esd).GetCentrality()){
\r
282 header->SetCentrality(const_cast<AliESDEvent&>(esd).GetCentrality());
\r
285 header->SetCentrality(0);
\r
287 if(const_cast<AliESDEvent&>(esd).GetEventplane()){
\r
288 header->SetEventplane(const_cast<AliESDEvent&>(esd).GetEventplane());
\r
291 header->SetEventplane(0);
\r
296 header->SetFiredTriggerClasses(esd.GetFiredTriggerClasses());
\r
297 header->SetTriggerMask(esd.GetTriggerMask());
\r
298 header->SetTriggerCluster(esd.GetTriggerCluster());
\r
299 header->SetL0TriggerInputs(esd.GetHeader()->GetL0TriggerInputs());
\r
300 header->SetL1TriggerInputs(esd.GetHeader()->GetL1TriggerInputs());
\r
301 header->SetL2TriggerInputs(esd.GetHeader()->GetL2TriggerInputs());
\r
303 header->SetMagneticField(esd.GetMagneticField());
\r
304 header->SetMuonMagFieldScale(esd.GetCurrentDip()/6000.);
\r
305 header->SetZDCN1Energy(esd.GetZDCN1Energy());
\r
306 header->SetZDCP1Energy(esd.GetZDCP1Energy());
\r
307 header->SetZDCN2Energy(esd.GetZDCN2Energy());
\r
308 header->SetZDCP2Energy(esd.GetZDCP2Energy());
\r
309 header->SetZDCEMEnergy(esd.GetZDCEMEnergy(0),esd.GetZDCEMEnergy(1));
\r
311 // ITS Cluster Multiplicty
\r
312 const AliMultiplicity *mult = esd.GetMultiplicity();
\r
313 for (Int_t ilay = 0; ilay < 6; ilay++) header->SetITSClusters(ilay, mult->GetNumberOfITSClusters(ilay));
\r
315 // TPC only Reference Multiplicty
\r
316 Int_t refMult = fTPCaloneTrackCuts ? (Short_t)fTPCaloneTrackCuts->GetReferenceMultiplicity(&esd, kTRUE) : -1;
\r
317 header->SetTPConlyRefMultiplicity(refMult);
\r
320 Float_t diamxy[2]={esd.GetDiamondX(),esd.GetDiamondY()};
\r
321 Float_t diamcov[3];
\r
322 esd.GetDiamondCovXY(diamcov);
\r
323 header->SetDiamond(diamxy,diamcov);
\r
324 header->SetDiamondZ(esd.GetDiamondZ(),esd.GetSigma2DiamondZ());
\r
326 // VZERO channel equalization factors for event-plane reconstruction
\r
327 header->SetVZEROEqFactors(esd.GetVZEROEqFactors());
\r
332 //______________________________________________________________________________
\r
333 void AliAnalysisTaskESDfilter::ConvertCascades(const AliESDEvent& esd)
\r
335 // Convert the cascades part of the ESD.
\r
336 // Return the number of cascades
\r
338 AliCodeTimerAuto("",0);
\r
340 // Create vertices starting from the most complex objects
\r
341 Double_t chi2 = 0.;
\r
343 const AliESDVertex* vtx = esd.GetPrimaryVertex();
\r
344 Double_t pos[3] = { 0. };
\r
345 Double_t covVtx[6] = { 0. };
\r
346 Double_t momBach[3]={0.};
\r
347 Double_t covTr[21]={0.};
\r
348 Double_t pid[10]={0.};
\r
349 AliAODPid* detpid(0x0);
\r
350 AliAODVertex* vV0FromCascade(0x0);
\r
351 AliAODv0* aodV0(0x0);
\r
352 AliAODcascade* aodCascade(0x0);
\r
353 AliAODTrack* aodTrack(0x0);
\r
354 Double_t momPos[3]={0.};
\r
355 Double_t momNeg[3] = { 0. };
\r
356 Double_t momPosAtV0vtx[3]={0.};
\r
357 Double_t momNegAtV0vtx[3]={0.};
\r
359 TClonesArray& verticesArray = Vertices();
\r
360 TClonesArray& tracksArray = Tracks();
\r
361 TClonesArray& cascadesArray = Cascades();
\r
363 // Cascades (Modified by A.Maire - February 2009)
\r
364 for (Int_t nCascade = 0; nCascade < esd.GetNumberOfCascades(); ++nCascade) {
\r
368 AliESDcascade *esdCascade = esd.GetCascade(nCascade);
\r
369 Int_t idxPosFromV0Dghter = esdCascade->GetPindex();
\r
370 Int_t idxNegFromV0Dghter = esdCascade->GetNindex();
\r
371 Int_t idxBachFromCascade = esdCascade->GetBindex();
\r
373 AliESDtrack *esdCascadePos = esd.GetTrack( idxPosFromV0Dghter);
\r
374 AliESDtrack *esdCascadeNeg = esd.GetTrack( idxNegFromV0Dghter);
\r
375 AliESDtrack *esdCascadeBach = esd.GetTrack( idxBachFromCascade);
\r
377 // Identification of the V0 within the esdCascade (via both daughter track indices)
\r
378 AliESDv0 * currentV0 = 0x0;
\r
379 Int_t idxV0FromCascade = -1;
\r
381 for (Int_t iV0=0; iV0<esd.GetNumberOfV0s(); ++iV0) {
\r
383 currentV0 = esd.GetV0(iV0);
\r
384 Int_t posCurrentV0 = currentV0->GetPindex();
\r
385 Int_t negCurrentV0 = currentV0->GetNindex();
\r
387 if (posCurrentV0==idxPosFromV0Dghter && negCurrentV0==idxNegFromV0Dghter) {
\r
388 idxV0FromCascade = iV0;
\r
393 if(idxV0FromCascade < 0){
\r
394 printf("Cascade - no matching for the V0 (index V0 = -1) ! Skip ... \n");
\r
396 }// a priori, useless check, but safer ... in case of pb with tracks "out of bounds"
\r
398 AliESDv0 *esdV0FromCascade = esd.GetV0(idxV0FromCascade);
\r
400 // 1 - Cascade selection
\r
402 // AliESDVertex *esdPrimVtx = new AliESDVertex(*(esd.GetPrimaryVertex()));
\r
403 // TList cascadeObjects;
\r
404 // cascadeObjects.AddAt(esdV0FromCascade, 0);
\r
405 // cascadeObjects.AddAt(esdCascadePos, 1);
\r
406 // cascadeObjects.AddAt(esdCascadeNeg, 2);
\r
407 // cascadeObjects.AddAt(esdCascade, 3);
\r
408 // cascadeObjects.AddAt(esdCascadeBach, 4);
\r
409 // cascadeObjects.AddAt(esdPrimVtx, 5);
\r
411 // UInt_t selectCascade = 0;
\r
412 // if (fCascadeFilter) {
\r
413 // // selectCascade = fCascadeFilter->IsSelected(&cascadeObjects);
\r
414 // // FIXME AliESDCascadeCuts to be implemented ...
\r
416 // // Here we may encounter a moot point at the V0 level
\r
417 // // between the cascade selections and the V0 ones :
\r
418 // // the V0 selected along with the cascade (secondary V0) may
\r
419 // // usually be removed from the dedicated V0 selections (prim V0) ...
\r
420 // // -> To be discussed !
\r
422 // // this is a little awkward but otherwise the
\r
423 // // list wants to access the pointer (delete it)
\r
424 // // again when going out of scope
\r
425 // delete cascadeObjects.RemoveAt(5); // esdPrimVtx created via copy construct
\r
427 // if (!selectCascade)
\r
431 // delete cascadeObjects.RemoveAt(5); // esdPrimVtx created via copy construct
\r
435 // 2 - Add the cascade vertex
\r
437 esdCascade->GetXYZcascade(pos[0], pos[1], pos[2]);
\r
438 esdCascade->GetPosCovXi(covVtx);
\r
439 chi2 = esdCascade->GetChi2Xi();
\r
441 AliAODVertex *vCascade = new(verticesArray[fNumberOfVertices++]) AliAODVertex( pos,
\r
443 chi2, // FIXME = Chi2/NDF will be needed
\r
446 AliAODVertex::kCascade);
\r
447 fPrimaryVertex->AddDaughter(vCascade);
\r
449 // if (fDebug > 2) {
\r
450 // printf("---- Cascade / Cascade Vertex (AOD) : \n");
\r
451 // vCascade->Print();
\r
454 if(esd.GetTOFHeader() && fIsPidOwner) fESDpid->SetTOFResponse(const_cast<AliESDEvent*>(&esd), (AliESDpid::EStartTimeType_t)fTimeZeroType); //in case of AOD production strating form LHC10e without Tender.
\r
457 // 3 - Add the bachelor track from the cascade
\r
459 if (!fUsedTrack[idxBachFromCascade]) {
\r
461 esdCascadeBach->GetPxPyPz(momBach);
\r
462 esdCascadeBach->GetXYZ(pos);
\r
463 esdCascadeBach->GetCovarianceXYZPxPyPz(covTr);
\r
464 esdCascadeBach->GetESDpid(pid);
\r
466 fUsedTrack[idxBachFromCascade] = kTRUE;
\r
467 UInt_t selectInfo = 0;
\r
468 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdCascadeBach);
\r
469 if (fMChandler) fMChandler->SelectParticle(esdCascadeBach->GetLabel());
\r
470 aodTrack = new(tracksArray[fNumberOfTracks++]) AliAODTrack(esdCascadeBach->GetID(),
\r
471 esdCascadeBach->GetLabel(),
\r
475 kFALSE, // Why kFALSE for "isDCA" ? FIXME
\r
477 (Short_t)esdCascadeBach->GetSign(),
\r
478 esdCascadeBach->GetITSClusterMap(),
\r
481 kTRUE, // usedForVtxFit = kFALSE ? FIXME
\r
482 vtx->UsesTrack(esdCascadeBach->GetID()),
\r
483 AliAODTrack::kSecondary,
\r
485 aodTrack->SetTPCClusterMap(esdCascadeBach->GetTPCClusterMap());
\r
486 aodTrack->SetTPCSharedMap (esdCascadeBach->GetTPCSharedMap());
\r
487 aodTrack->SetChi2perNDF(Chi2perNDF(esdCascadeBach));
\r
488 aodTrack->SetTPCPointsF(esdCascadeBach->GetTPCNclsF());
\r
489 fAODTrackRefs->AddAt(aodTrack,idxBachFromCascade);
\r
491 if (esdCascadeBach->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
492 aodTrack->ConvertAliPIDtoAODPID();
\r
493 aodTrack->SetFlags(esdCascadeBach->GetStatus());
\r
494 SetAODPID(esdCascadeBach,aodTrack,detpid);
\r
497 aodTrack = static_cast<AliAODTrack*>( fAODTrackRefs->At(idxBachFromCascade) );
\r
500 vCascade->AddDaughter(aodTrack);
\r
502 // if (fDebug > 4) {
\r
503 // printf("---- Cascade / bach dghter : \n");
\r
504 // aodTrack->Print();
\r
508 // 4 - Add the V0 from the cascade.
\r
509 // = V0vtx + both pos and neg daughter tracks + the aodV0 itself
\r
512 if ( !fUsedV0[idxV0FromCascade] ) {
\r
513 // 4.A - if VO structure hasn't been created yet
\r
515 // 4.A.1 - Create the V0 vertex of the cascade
\r
517 esdV0FromCascade->GetXYZ(pos[0], pos[1], pos[2]);
\r
518 esdV0FromCascade->GetPosCov(covVtx);
\r
519 chi2 = esdV0FromCascade->GetChi2V0(); // = chi2/NDF since NDF = 2*2-3 ?
\r
521 vV0FromCascade = new(verticesArray[fNumberOfVertices++]) AliAODVertex(pos,
\r
525 idxV0FromCascade, //id of ESDv0
\r
526 AliAODVertex::kV0);
\r
528 // one V0 can be used by several cascades.
\r
529 // So, one AOD V0 vtx can have several parent vtx.
\r
530 // This is not directly allowed by AliAODvertex.
\r
531 // Setting the parent vtx (here = param "vCascade") doesn't lead to a crash
\r
532 // but to a problem of consistency within AODEvent.
\r
533 // -> See below paragraph 4.B, for the proposed treatment of such a case.
\r
535 // Add the vV0FromCascade to the aodVOVtxRefs
\r
536 fAODV0VtxRefs->AddAt(vV0FromCascade,idxV0FromCascade);
\r
539 // 4.A.2 - Add the positive tracks from the V0
\r
541 esdCascadePos->GetPxPyPz(momPos);
\r
542 esdCascadePos->GetXYZ(pos);
\r
543 esdCascadePos->GetCovarianceXYZPxPyPz(covTr);
\r
544 esdCascadePos->GetESDpid(pid);
\r
547 if (!fUsedTrack[idxPosFromV0Dghter]) {
\r
548 fUsedTrack[idxPosFromV0Dghter] = kTRUE;
\r
550 UInt_t selectInfo = 0;
\r
551 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdCascadePos);
\r
552 if(fMChandler) fMChandler->SelectParticle(esdCascadePos->GetLabel());
\r
553 aodTrack = new(tracksArray[fNumberOfTracks++])
\r
554 AliAODTrack( esdCascadePos->GetID(),
\r
555 esdCascadePos->GetLabel(),
\r
559 kFALSE, // Why kFALSE for "isDCA" ? FIXME
\r
561 (Short_t)esdCascadePos->GetSign(),
\r
562 esdCascadePos->GetITSClusterMap(),
\r
565 kTRUE, // usedForVtxFit = kFALSE ? FIXME
\r
566 vtx->UsesTrack(esdCascadePos->GetID()),
\r
567 AliAODTrack::kSecondary,
\r
569 aodTrack->SetTPCClusterMap(esdCascadePos->GetTPCClusterMap());
\r
570 aodTrack->SetTPCSharedMap (esdCascadePos->GetTPCSharedMap());
\r
571 aodTrack->SetChi2perNDF(Chi2perNDF(esdCascadePos));
\r
572 aodTrack->SetTPCPointsF(esdCascadePos->GetTPCNclsF());
\r
573 fAODTrackRefs->AddAt(aodTrack,idxPosFromV0Dghter);
\r
575 if (esdCascadePos->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
576 aodTrack->ConvertAliPIDtoAODPID();
\r
577 aodTrack->SetFlags(esdCascadePos->GetStatus());
\r
578 SetAODPID(esdCascadePos,aodTrack,detpid);
\r
581 aodTrack = static_cast<AliAODTrack*>(fAODTrackRefs->At(idxPosFromV0Dghter));
\r
583 vV0FromCascade->AddDaughter(aodTrack);
\r
586 // 4.A.3 - Add the negative tracks from the V0
\r
588 esdCascadeNeg->GetPxPyPz(momNeg);
\r
589 esdCascadeNeg->GetXYZ(pos);
\r
590 esdCascadeNeg->GetCovarianceXYZPxPyPz(covTr);
\r
591 esdCascadeNeg->GetESDpid(pid);
\r
594 if (!fUsedTrack[idxNegFromV0Dghter]) {
\r
595 fUsedTrack[idxNegFromV0Dghter] = kTRUE;
\r
597 UInt_t selectInfo = 0;
\r
598 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdCascadeNeg);
\r
599 if(fMChandler)fMChandler->SelectParticle(esdCascadeNeg->GetLabel());
\r
600 aodTrack = new(tracksArray[fNumberOfTracks++]) AliAODTrack( esdCascadeNeg->GetID(),
\r
601 esdCascadeNeg->GetLabel(),
\r
605 kFALSE, // Why kFALSE for "isDCA" ? FIXME
\r
607 (Short_t)esdCascadeNeg->GetSign(),
\r
608 esdCascadeNeg->GetITSClusterMap(),
\r
611 kTRUE, // usedForVtxFit = kFALSE ? FIXME
\r
612 vtx->UsesTrack(esdCascadeNeg->GetID()),
\r
613 AliAODTrack::kSecondary,
\r
615 aodTrack->SetTPCClusterMap(esdCascadeNeg->GetTPCClusterMap());
\r
616 aodTrack->SetTPCSharedMap (esdCascadeNeg->GetTPCSharedMap());
\r
617 aodTrack->SetChi2perNDF(Chi2perNDF(esdCascadeNeg));
\r
618 aodTrack->SetTPCPointsF(esdCascadeNeg->GetTPCNclsF());
\r
619 fAODTrackRefs->AddAt(aodTrack,idxNegFromV0Dghter);
\r
621 if (esdCascadeNeg->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
622 aodTrack->ConvertAliPIDtoAODPID();
\r
623 aodTrack->SetFlags(esdCascadeNeg->GetStatus());
\r
624 SetAODPID(esdCascadeNeg,aodTrack,detpid);
\r
627 aodTrack = static_cast<AliAODTrack*>(fAODTrackRefs->At(idxNegFromV0Dghter));
\r
630 vV0FromCascade->AddDaughter(aodTrack);
\r
633 // 4.A.4 - Add the V0 from cascade to the V0 array
\r
635 Double_t dcaV0Daughters = esdV0FromCascade->GetDcaV0Daughters();
\r
636 Double_t dcaV0ToPrimVertex = esdV0FromCascade->GetD( esd.GetPrimaryVertex()->GetX(),
\r
637 esd.GetPrimaryVertex()->GetY(),
\r
638 esd.GetPrimaryVertex()->GetZ() );
\r
639 esdV0FromCascade->GetPPxPyPz( momPosAtV0vtx[0],momPosAtV0vtx[1],momPosAtV0vtx[2] );
\r
640 esdV0FromCascade->GetNPxPyPz( momNegAtV0vtx[0],momNegAtV0vtx[1],momNegAtV0vtx[2] );
\r
642 Double_t dcaDaughterToPrimVertex[2] = { 999., 999.}; // ..[0] = DCA in (x,y) for Pos and ..[1] = Neg
\r
643 dcaDaughterToPrimVertex[0] = TMath::Abs(esdCascadePos->GetD( esd.GetPrimaryVertex()->GetX(),
\r
644 esd.GetPrimaryVertex()->GetY(),
\r
645 esd.GetMagneticField()) );
\r
646 dcaDaughterToPrimVertex[1] = TMath::Abs(esdCascadeNeg->GetD( esd.GetPrimaryVertex()->GetX(),
\r
647 esd.GetPrimaryVertex()->GetY(),
\r
648 esd.GetMagneticField()) );
\r
650 aodV0 = new(V0s()[fNumberOfV0s++]) AliAODv0( vV0FromCascade,
\r
652 dcaV0ToPrimVertex,
\r
655 dcaDaughterToPrimVertex);
\r
656 // set the aod v0 on-the-fly status
\r
657 aodV0->SetOnFlyStatus(esdV0FromCascade->GetOnFlyStatus());
\r
659 // Add the aodV0 to the aodVORefs
\r
660 fAODV0Refs->AddAt(aodV0,idxV0FromCascade);
\r
662 fUsedV0[idxV0FromCascade] = kTRUE;
\r
665 // 4.B - if V0 structure already used
\r
668 // one V0 can be used by several cascades (frequent in PbPb evts) :
\r
669 // same V0 which used but attached to different bachelor tracks
\r
670 // -> aodVORefs and fAODV0VtxRefs are needed.
\r
671 // Goal : avoid a redundancy of the info in "Vertices" and "v0s" clones array.
\r
673 vV0FromCascade = static_cast<AliAODVertex*>( fAODV0VtxRefs->At(idxV0FromCascade) );
\r
674 aodV0 = static_cast<AliAODv0*> ( fAODV0Refs ->At(idxV0FromCascade) );
\r
676 // - Treatment of the parent for such a "re-used" V0 :
\r
677 // Insert the cascade that reuses the V0 vertex in the lineage chain
\r
678 // Before : vV0 -> vCascade1 -> vPrimary
\r
679 // - Hyp : cascade2 uses the same V0 as cascade1
\r
680 // After : vV0 -> vCascade2 -> vCascade1 -> vPrimary
\r
682 AliAODVertex *vCascadePreviousParent = static_cast<AliAODVertex*> (vV0FromCascade->GetParent());
\r
683 vV0FromCascade->SetParent(vCascade);
\r
684 vCascade ->SetParent(vCascadePreviousParent);
\r
687 // printf("---- Cascade / Lineage insertion\n"
\r
688 // "Parent of V0 vtx = Cascade vtx %p\n"
\r
689 // "Parent of the cascade vtx = Cascade vtx %p\n"
\r
690 // "Parent of the parent cascade vtx = Cascade vtx %p\n",
\r
691 // static_cast<void*> (vV0FromCascade->GetParent()),
\r
692 // static_cast<void*> (vCascade->GetParent()),
\r
693 // static_cast<void*> (vCascadePreviousParent->GetParent()) );
\r
695 }// end if V0 structure already used
\r
697 // if (fDebug > 2) {
\r
698 // printf("---- Cascade / V0 vertex: \n");
\r
699 // vV0FromCascade->Print();
\r
702 // if (fDebug > 4) {
\r
703 // printf("---- Cascade / pos dghter : \n");
\r
704 // aodTrack->Print();
\r
705 // printf("---- Cascade / neg dghter : \n");
\r
706 // aodTrack->Print();
\r
707 // printf("---- Cascade / aodV0 : \n");
\r
711 // In any case (used V0 or not), add the V0 vertex to the cascade one.
\r
712 vCascade->AddDaughter(vV0FromCascade);
\r
715 // 5 - Add the primary track of the cascade (if any)
\r
718 // 6 - Add the cascade to the AOD array of cascades
\r
720 Double_t dcaBachToPrimVertexXY = TMath::Abs(esdCascadeBach->GetD(esd.GetPrimaryVertex()->GetX(),
\r
721 esd.GetPrimaryVertex()->GetY(),
\r
722 esd.GetMagneticField()) );
\r
724 Double_t momBachAtCascadeVtx[3]={0.};
\r
726 esdCascade->GetBPxPyPz(momBachAtCascadeVtx[0], momBachAtCascadeVtx[1], momBachAtCascadeVtx[2]);
\r
728 aodCascade = new(cascadesArray[fNumberOfCascades++]) AliAODcascade( vCascade,
\r
729 esdCascade->Charge(),
\r
730 esdCascade->GetDcaXiDaughters(),
\r
732 // DCAXiToPrimVtx -> needs to be calculated ----|
\r
733 // doesn't exist at ESD level;
\r
734 // See AODcascade::DcaXiToPrimVertex(Double, Double, Double)
\r
735 dcaBachToPrimVertexXY,
\r
736 momBachAtCascadeVtx,
\r
740 printf("---- Cascade / AOD cascade : \n\n");
\r
741 aodCascade->PrintXi(fPrimaryVertex->GetX(), fPrimaryVertex->GetY(), fPrimaryVertex->GetZ());
\r
744 } // end of the loop on cascades
\r
746 Cascades().Expand(fNumberOfCascades);
\r
749 //______________________________________________________________________________
\r
750 void AliAnalysisTaskESDfilter::ConvertV0s(const AliESDEvent& esd)
\r
752 // Access to the AOD container of V0s
\r
754 AliCodeTimerAuto("",0);
\r
760 Double_t pos[3] = { 0. };
\r
761 Double_t chi2(0.0);
\r
762 Double_t covVtx[6] = { 0. };
\r
763 Double_t momPos[3]={0.};
\r
764 Double_t covTr[21]={0.};
\r
765 Double_t pid[10]={0.};
\r
766 AliAODTrack* aodTrack(0x0);
\r
767 AliAODPid* detpid(0x0);
\r
768 Double_t momNeg[3]={0.};
\r
769 Double_t momPosAtV0vtx[3]={0.};
\r
770 Double_t momNegAtV0vtx[3]={0.};
\r
772 for (Int_t nV0 = 0; nV0 < esd.GetNumberOfV0s(); ++nV0)
\r
774 if (fUsedV0[nV0]) continue; // skip if already added to the AOD
\r
776 AliESDv0 *v0 = esd.GetV0(nV0);
\r
777 Int_t posFromV0 = v0->GetPindex();
\r
778 Int_t negFromV0 = v0->GetNindex();
\r
782 AliESDVertex *esdVtx = new AliESDVertex(*(esd.GetPrimaryVertex()));
\r
783 AliESDtrack *esdV0Pos = esd.GetTrack(posFromV0);
\r
784 AliESDtrack *esdV0Neg = esd.GetTrack(negFromV0);
\r
786 v0objects.AddAt(v0, 0);
\r
787 v0objects.AddAt(esdV0Pos, 1);
\r
788 v0objects.AddAt(esdV0Neg, 2);
\r
789 v0objects.AddAt(esdVtx, 3);
\r
790 UInt_t selectV0 = 0;
\r
792 selectV0 = fV0Filter->IsSelected(&v0objects);
\r
793 // this is a little awkward but otherwise the
\r
794 // list wants to access the pointer (delete it)
\r
795 // again when going out of scope
\r
796 delete v0objects.RemoveAt(3); // esdVtx created via copy construct
\r
802 delete v0objects.RemoveAt(3); // esdVtx created via copy construct
\r
806 v0->GetXYZ(pos[0], pos[1], pos[2]);
\r
808 if (!fOldESDformat) {
\r
809 chi2 = v0->GetChi2V0(); // = chi2/NDF since NDF = 2*2-3
\r
810 v0->GetPosCov(covVtx);
\r
813 for (Int_t i = 0; i < 6; i++) covVtx[i] = 0.;
\r
817 AliAODVertex * vV0 =
\r
818 new(Vertices()[fNumberOfVertices++]) AliAODVertex(pos,
\r
823 AliAODVertex::kV0);
\r
824 fPrimaryVertex->AddDaughter(vV0);
\r
827 // Add the positive tracks from the V0
\r
830 esdV0Pos->GetPxPyPz(momPos);
\r
831 esdV0Pos->GetXYZ(pos);
\r
832 esdV0Pos->GetCovarianceXYZPxPyPz(covTr);
\r
833 esdV0Pos->GetESDpid(pid);
\r
835 const AliESDVertex *vtx = esd.GetPrimaryVertex();
\r
837 if (!fUsedTrack[posFromV0]) {
\r
838 fUsedTrack[posFromV0] = kTRUE;
\r
839 UInt_t selectInfo = 0;
\r
840 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdV0Pos);
\r
841 if(fMChandler)fMChandler->SelectParticle(esdV0Pos->GetLabel());
\r
842 aodTrack = new(Tracks()[fNumberOfTracks++]) AliAODTrack(esdV0Pos->GetID(),
\r
843 esdV0Pos->GetLabel(),
\r
849 (Short_t)esdV0Pos->GetSign(),
\r
850 esdV0Pos->GetITSClusterMap(),
\r
853 kTRUE, // check if this is right
\r
854 vtx->UsesTrack(esdV0Pos->GetID()),
\r
855 AliAODTrack::kSecondary,
\r
857 aodTrack->SetTPCClusterMap(esdV0Pos->GetTPCClusterMap());
\r
858 aodTrack->SetTPCSharedMap (esdV0Pos->GetTPCSharedMap());
\r
859 aodTrack->SetChi2perNDF(Chi2perNDF(esdV0Pos));
\r
860 aodTrack->SetTPCPointsF(esdV0Pos->GetTPCNclsF());
\r
861 fAODTrackRefs->AddAt(aodTrack,posFromV0);
\r
862 // if (fDebug > 0) printf("-------------------Bo: pos track from original pt %.3f \n",aodTrack->Pt());
\r
863 if (esdV0Pos->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
864 aodTrack->ConvertAliPIDtoAODPID();
\r
865 aodTrack->SetFlags(esdV0Pos->GetStatus());
\r
866 SetAODPID(esdV0Pos,aodTrack,detpid);
\r
869 aodTrack = static_cast<AliAODTrack*>(fAODTrackRefs->At(posFromV0));
\r
870 // if (fDebug > 0) printf("-------------------Bo pos track from refArray pt %.3f \n",aodTrack->Pt());
\r
872 vV0->AddDaughter(aodTrack);
\r
874 // Add the negative tracks from the V0
\r
876 esdV0Neg->GetPxPyPz(momNeg);
\r
877 esdV0Neg->GetXYZ(pos);
\r
878 esdV0Neg->GetCovarianceXYZPxPyPz(covTr);
\r
879 esdV0Neg->GetESDpid(pid);
\r
881 if (!fUsedTrack[negFromV0]) {
\r
882 fUsedTrack[negFromV0] = kTRUE;
\r
883 UInt_t selectInfo = 0;
\r
884 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdV0Neg);
\r
885 if(fMChandler)fMChandler->SelectParticle(esdV0Neg->GetLabel());
\r
886 aodTrack = new(Tracks()[fNumberOfTracks++]) AliAODTrack(esdV0Neg->GetID(),
\r
887 esdV0Neg->GetLabel(),
\r
893 (Short_t)esdV0Neg->GetSign(),
\r
894 esdV0Neg->GetITSClusterMap(),
\r
897 kTRUE, // check if this is right
\r
898 vtx->UsesTrack(esdV0Neg->GetID()),
\r
899 AliAODTrack::kSecondary,
\r
901 aodTrack->SetTPCClusterMap(esdV0Neg->GetTPCClusterMap());
\r
902 aodTrack->SetTPCSharedMap (esdV0Neg->GetTPCSharedMap());
\r
903 aodTrack->SetChi2perNDF(Chi2perNDF(esdV0Neg));
\r
904 aodTrack->SetTPCPointsF(esdV0Neg->GetTPCNclsF());
\r
906 fAODTrackRefs->AddAt(aodTrack,negFromV0);
\r
907 // if (fDebug > 0) printf("-------------------Bo: neg track from original pt %.3f \n",aodTrack->Pt());
\r
908 if (esdV0Neg->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
909 aodTrack->ConvertAliPIDtoAODPID();
\r
910 aodTrack->SetFlags(esdV0Neg->GetStatus());
\r
911 SetAODPID(esdV0Neg,aodTrack,detpid);
\r
914 aodTrack = static_cast<AliAODTrack*>(fAODTrackRefs->At(negFromV0));
\r
915 // if (fDebug > 0) printf("-------------------Bo neg track from refArray pt %.3f \n",aodTrack->Pt());
\r
917 vV0->AddDaughter(aodTrack);
\r
920 // Add the V0 the V0 array as well
\r
922 Double_t dcaV0Daughters = v0->GetDcaV0Daughters();
\r
923 Double_t dcaV0ToPrimVertex = v0->GetD(esd.GetPrimaryVertex()->GetX(),
\r
924 esd.GetPrimaryVertex()->GetY(),
\r
925 esd.GetPrimaryVertex()->GetZ());
\r
927 v0->GetPPxPyPz(momPosAtV0vtx[0],momPosAtV0vtx[1],momPosAtV0vtx[2]);
\r
928 v0->GetNPxPyPz(momNegAtV0vtx[0],momNegAtV0vtx[1],momNegAtV0vtx[2]);
\r
930 Double_t dcaDaughterToPrimVertex[2] = { 999., 999.}; // ..[0] = DCA in (x,y) for Pos and ..[1] = Neg
\r
931 dcaDaughterToPrimVertex[0] = TMath::Abs(esdV0Pos->GetD( esd.GetPrimaryVertex()->GetX(),
\r
932 esd.GetPrimaryVertex()->GetY(),
\r
933 esd.GetMagneticField()) );
\r
934 dcaDaughterToPrimVertex[1] = TMath::Abs(esdV0Neg->GetD( esd.GetPrimaryVertex()->GetX(),
\r
935 esd.GetPrimaryVertex()->GetY(),
\r
936 esd.GetMagneticField()) );
\r
938 AliAODv0* aodV0 = new(V0s()[fNumberOfV0s++]) AliAODv0(vV0,
\r
943 dcaDaughterToPrimVertex);
\r
945 // set the aod v0 on-the-fly status
\r
946 aodV0->SetOnFlyStatus(v0->GetOnFlyStatus());
\r
947 }//End of loop on V0s
\r
949 V0s().Expand(fNumberOfV0s);
\r
952 //______________________________________________________________________________
\r
953 void AliAnalysisTaskESDfilter::ConvertTPCOnlyTracks(const AliESDEvent& esd)
\r
955 // Convert TPC only tracks
\r
956 // Here we have wo hybrid appraoch to remove fakes
\r
957 // ******* ITSTPC ********
\r
958 // Uses a cut on the ITS properties to select global tracks
\r
959 // which are than marked as HybdridITSTPC for the remainder
\r
960 // the TPC only tracks are flagged as HybridITSTPConly.
\r
961 // Note, in order not to get fakes back in the TPC cuts, one needs
\r
962 // two "ITS" cuts one tight (1) (to throw out fakes) and one lose (2) (to NOT flag the trakcs in the TPC only)
\r
963 // using cut number (3)
\r
964 // so fHybridFilterMask == (1)|(2) fTPCFilterMask = (3), Usercode needs to slect with mask = (1)|(3) and track->IsHybridITSTPC()
\r
965 // ******* TPC ********
\r
966 // Here, only TPC tracks are flagged that pass the tight ITS cuts and tracks that pass the TPC cuts and NOT the loose ITS cuts
\r
967 // the ITS cuts neeed to be added to the filter as extra cuts, since here the selections info is reset in the global and put to the TPC only track
\r
969 AliCodeTimerAuto("",0);
\r
971 // Loop over the tracks and extract and mask out all aod tracks that pass the selections for AODt racks
\r
972 for(int it = 0;it < fNumberOfTracks;++it)
\r
974 AliAODTrack *tr = (AliAODTrack*)(Tracks().At(it));
\r
976 UInt_t map = tr->GetFilterMap();
\r
977 if(map&fTPCConstrainedFilterMask){
\r
978 // we only reset the track select ionfo, no deletion...
\r
979 tr->SetFilterMap(map&~fTPCConstrainedFilterMask);
\r
981 if(map&fHybridFilterMaskTPCCG){
\r
982 // this is one part of the hybrid tracks
\r
983 // the others not passing the selection will be TPC only selected below
\r
984 tr->SetIsHybridTPCConstrainedGlobal(kTRUE);
\r
987 // Loop over the ESD trcks and pick out the tracks passing TPC only cuts
\r
990 const AliESDVertex *vtxSPD = esd.GetPrimaryVertexSPD();
\r
991 const AliESDVertex *vtx = esd.GetPrimaryVertex();
\r
993 Double_t pos[3] = { 0. };
\r
994 Double_t covTr[21]={0.};
\r
995 Double_t pid[10]={0.};
\r
996 Double_t p[3] = { 0. };
\r
998 Double_t pDCA[3] = { 0. }; // momentum at DCA
\r
999 Double_t rDCA[3] = { 0. }; // position at DCA
\r
1000 Float_t dDCA[2] = {0.}; // DCA to the vertex d and z
\r
1001 Float_t cDCA[3] = {0.}; // covariance of impact parameters
\r
1004 AliAODTrack* aodTrack(0x0);
\r
1006 // account for change in pT after the constraint
\r
1007 Float_t ptMax = 1E10;
\r
1008 Float_t ptMin = 0;
\r
1009 for(int i = 0;i<32;i++){
\r
1010 if(fTPCConstrainedFilterMask&(1<<i)){
\r
1011 AliESDtrackCuts*cuts = (AliESDtrackCuts*)fTrackFilter->GetCuts()->At(i);
\r
1012 Float_t tmp1= 0,tmp2 = 0;
\r
1013 cuts->GetPtRange(tmp1,tmp2);
\r
1014 if(tmp1>ptMin)ptMin=tmp1;
\r
1015 if(tmp2<ptMax)ptMax=tmp2;
\r
1019 for (Int_t nTrack = 0; nTrack < esd.GetNumberOfTracks(); ++nTrack)
\r
1021 AliESDtrack* esdTrack = esd.GetTrack(nTrack); //carefull do not modify it othwise need to work with a copy
\r
1023 UInt_t selectInfo = 0;
\r
1024 Bool_t isHybridITSTPC = false;
\r
1026 // Track selection
\r
1027 if (fTrackFilter) {
\r
1028 selectInfo = fTrackFilter->IsSelected(esdTrack);
\r
1031 if(!(selectInfo&fHybridFilterMaskTPCCG)){
\r
1032 // not already selected tracks, use second part of hybrid tracks
\r
1033 isHybridITSTPC = true;
\r
1034 // too save space one could only store these...
\r
1037 selectInfo &= fTPCConstrainedFilterMask;
\r
1038 if (!selectInfo)continue;
\r
1039 if (fWriteHybridTPCCOnly&&!isHybridITSTPC)continue; // write only complementary tracks
\r
1040 // create a tpc only tracl
\r
1041 AliESDtrack *track = AliESDtrackCuts::GetTPCOnlyTrack(const_cast<AliESDEvent*>(&esd),esdTrack->GetID());
\r
1042 if(!track) continue;
\r
1044 if(track->Pt()>0.)
\r
1046 // only constrain tracks above threshold
\r
1047 AliExternalTrackParam exParam;
\r
1048 // take the B-field from the ESD, no 3D fieldMap available at this point
\r
1049 Bool_t relate = false;
\r
1050 relate = track->RelateToVertexTPC(vtxSPD,esd.GetMagneticField(),kVeryBig,&exParam);
\r
1055 // fetch the track parameters at the DCA (unconstraint)
\r
1056 if(track->GetTPCInnerParam()){
\r
1057 track->GetTPCInnerParam()->GetPxPyPz(pDCA);
\r
1058 track->GetTPCInnerParam()->GetXYZ(rDCA);
\r
1060 // get the DCA to the vertex:
\r
1061 track->GetImpactParametersTPC(dDCA,cDCA);
\r
1062 // set the constrained parameters to the track
\r
1063 track->Set(exParam.GetX(),exParam.GetAlpha(),exParam.GetParameter(),exParam.GetCovariance());
\r
1066 track->GetPxPyPz(p);
\r
1068 Float_t pT = track->Pt();
\r
1069 if(pT<ptMin||pT>ptMax){
\r
1077 track->GetXYZ(pos);
\r
1078 track->GetCovarianceXYZPxPyPz(covTr);
\r
1079 track->GetESDpid(pid);
\r
1081 if(fMChandler)fMChandler->SelectParticle(esdTrack->GetLabel());
\r
1082 aodTrack = new(Tracks()[fNumberOfTracks++]) AliAODTrack((track->GetID()+1)*-1,
\r
1083 track->GetLabel(),
\r
1089 (Short_t)track->GetSign(),
\r
1090 track->GetITSClusterMap(),
\r
1093 kTRUE, // check if this is right
\r
1094 vtx->UsesTrack(track->GetID()),
\r
1095 AliAODTrack::kPrimary,
\r
1097 aodTrack->SetIsHybridTPCConstrainedGlobal(isHybridITSTPC);
\r
1098 aodTrack->SetTPCClusterMap(track->GetTPCClusterMap());
\r
1099 aodTrack->SetTPCSharedMap (track->GetTPCSharedMap());
\r
1100 aodTrack->SetIsTPCConstrained(kTRUE);
\r
1101 Float_t ndf = track->GetTPCNcls()+1 - 5 ;
\r
1103 aodTrack->SetChi2perNDF(track->GetConstrainedChi2TPC());
\r
1106 aodTrack->SetChi2perNDF(-1);
\r
1109 // set the DCA values to the AOD track
\r
1110 aodTrack->SetPxPyPzAtDCA(pDCA[0],pDCA[1],pDCA[2]);
\r
1111 aodTrack->SetXYAtDCA(rDCA[0],rDCA[1]);
\r
1112 aodTrack->SetDCA(dDCA[0],dDCA[1]);
\r
1114 aodTrack->SetFlags(track->GetStatus());
\r
1115 aodTrack->SetTPCPointsF(track->GetTPCNclsF());
\r
1118 } // end of loop on tracks
\r
1123 void AliAnalysisTaskESDfilter::ConvertGlobalConstrainedTracks(const AliESDEvent& esd)
\r
1126 // Here we have the option to store the complement from global constraint information
\r
1127 // to tracks passing tight cuts (1) in order not to get fakes back in, one needs
\r
1128 // two sets of cuts one tight (1) (to throw out fakes) and one lose (2) (fakes/bad tracks would pass (2) but not (1))
\r
1129 // using cut number (3) selects the tracks that complement (1) e.g. tracks witout ITS refit or cluster requirement
\r
1132 AliCodeTimerAuto("",0);
\r
1134 // Loop over the tracks and extract and mask out all aod tracks that pass the selections for AODt racks
\r
1135 for(int it = 0;it < fNumberOfTracks;++it)
\r
1137 AliAODTrack *tr = (AliAODTrack*)(Tracks().At(it));
\r
1139 UInt_t map = tr->GetFilterMap();
\r
1140 if(map&fGlobalConstrainedFilterMask){
\r
1141 // we only reset the track select info, no deletion...
\r
1142 // mask reset mask in case track is already taken
\r
1143 tr->SetFilterMap(map&~fGlobalConstrainedFilterMask);
\r
1145 if(map&fHybridFilterMaskGCG){
\r
1146 // this is one part of the hybrid tracks
\r
1147 // the others not passing the selection will be the ones selected below
\r
1148 tr->SetIsHybridGlobalConstrainedGlobal(kTRUE);
\r
1151 // Loop over the ESD trcks and pick out the tracks passing the GlobalConstraint cuts
\r
1154 Double_t pos[3] = { 0. };
\r
1155 Double_t covTr[21]={0.};
\r
1156 Double_t pid[10]={0.};
\r
1157 Double_t p[3] = { 0. };
\r
1159 Double_t pDCA[3] = { 0. }; // momentum at DCA
\r
1160 Double_t rDCA[3] = { 0. }; // position at DCA
\r
1161 Float_t dDCA[2] = {0.}; // DCA to the vertex d and z
\r
1162 Float_t cDCA[3] = {0.}; // covariance of impact parameters
\r
1165 AliAODTrack* aodTrack(0x0);
\r
1166 const AliESDVertex *vtx = esd.GetPrimaryVertex();
\r
1168 // account for change in pT after the constraint
\r
1169 Float_t ptMax = 1E10;
\r
1170 Float_t ptMin = 0;
\r
1171 for(int i = 0;i<32;i++){
\r
1172 if(fGlobalConstrainedFilterMask&(1<<i)){
\r
1173 AliESDtrackCuts*cuts = (AliESDtrackCuts*)fTrackFilter->GetCuts()->At(i);
\r
1174 Float_t tmp1= 0,tmp2 = 0;
\r
1175 cuts->GetPtRange(tmp1,tmp2);
\r
1176 if(tmp1>ptMin)ptMin=tmp1;
\r
1177 if(tmp2<ptMax)ptMax=tmp2;
\r
1183 for (Int_t nTrack = 0; nTrack < esd.GetNumberOfTracks(); ++nTrack)
\r
1185 AliESDtrack* esdTrack = esd.GetTrack(nTrack); //carefull do not modify it othwise need to work with a copy
\r
1186 const AliExternalTrackParam * exParamGC = esdTrack->GetConstrainedParam();
\r
1187 if(!exParamGC)continue;
\r
1189 UInt_t selectInfo = 0;
\r
1190 Bool_t isHybridGC = false;
\r
1193 // Track selection
\r
1194 if (fTrackFilter) {
\r
1195 selectInfo = fTrackFilter->IsSelected(esdTrack);
\r
1199 if(!(selectInfo&fHybridFilterMaskGCG))isHybridGC = true;
\r
1200 if (fWriteHybridGCOnly&&!isHybridGC)continue; // write only complementary tracks
\r
1202 selectInfo &= fGlobalConstrainedFilterMask;
\r
1203 if (!selectInfo)continue;
\r
1204 // fetch the track parameters at the DCA (unconstrained)
\r
1205 esdTrack->GetPxPyPz(pDCA);
\r
1206 esdTrack->GetXYZ(rDCA);
\r
1207 // get the DCA to the vertex:
\r
1208 esdTrack->GetImpactParameters(dDCA,cDCA);
\r
1210 esdTrack->GetConstrainedPxPyPz(p);
\r
1213 Float_t pT = exParamGC->Pt();
\r
1214 if(pT<ptMin||pT>ptMax){
\r
1219 esdTrack->GetConstrainedXYZ(pos);
\r
1220 exParamGC->GetCovarianceXYZPxPyPz(covTr);
\r
1221 esdTrack->GetESDpid(pid);
\r
1222 if(fMChandler)fMChandler->SelectParticle(esdTrack->GetLabel());
\r
1223 aodTrack = new(Tracks()[fNumberOfTracks++]) AliAODTrack((esdTrack->GetID()+1)*-1,
\r
1224 esdTrack->GetLabel(),
\r
1230 (Short_t)esdTrack->GetSign(),
\r
1231 esdTrack->GetITSClusterMap(),
\r
1234 kTRUE, // check if this is right
\r
1235 vtx->UsesTrack(esdTrack->GetID()),
\r
1236 AliAODTrack::kPrimary,
\r
1238 aodTrack->SetIsHybridGlobalConstrainedGlobal(isHybridGC);
\r
1239 aodTrack->SetIsGlobalConstrained(kTRUE);
\r
1240 aodTrack->SetTPCClusterMap(esdTrack->GetTPCClusterMap());
\r
1241 aodTrack->SetTPCSharedMap (esdTrack->GetTPCSharedMap());
\r
1242 Float_t ndf = esdTrack->GetTPCNcls()+1 - 5 ;
\r
1244 aodTrack->SetChi2perNDF(esdTrack->GetConstrainedChi2TPC());
\r
1247 aodTrack->SetChi2perNDF(-1);
\r
1250 // set the DCA values to the AOD track
\r
1251 aodTrack->SetPxPyPzAtDCA(pDCA[0],pDCA[1],pDCA[2]);
\r
1252 aodTrack->SetXYAtDCA(rDCA[0],rDCA[1]);
\r
1253 aodTrack->SetDCA(dDCA[0],dDCA[1]);
\r
1255 aodTrack->SetFlags(esdTrack->GetStatus());
\r
1256 aodTrack->SetTPCPointsF(esdTrack->GetTPCNclsF());
\r
1257 } // end of loop on tracks
\r
1262 //______________________________________________________________________________
\r
1263 void AliAnalysisTaskESDfilter::ConvertTracks(const AliESDEvent& esd)
\r
1265 // Tracks (primary and orphan)
\r
1267 AliCodeTimerAuto("",0);
\r
1269 AliDebug(1,Form("NUMBER OF ESD TRACKS %5d\n", esd.GetNumberOfTracks()));
\r
1271 const AliESDVertex *vtx = esd.GetPrimaryVertex();
\r
1272 Double_t p[3] = { 0. };
\r
1273 Double_t pos[3] = { 0. };
\r
1274 Double_t covTr[21] = { 0. };
\r
1275 Double_t pid[10] = { 0. };
\r
1276 AliAODTrack* aodTrack(0x0);
\r
1277 AliAODPid* detpid(0x0);
\r
1279 for (Int_t nTrack = 0; nTrack < esd.GetNumberOfTracks(); ++nTrack)
\r
1281 if (fUsedTrack[nTrack]) continue;
\r
1283 AliESDtrack *esdTrack = esd.GetTrack(nTrack);
\r
1284 UInt_t selectInfo = 0;
\r
1286 // Track selection
\r
1287 if (fTrackFilter) {
\r
1288 selectInfo = fTrackFilter->IsSelected(esdTrack);
\r
1289 if (!selectInfo && !vtx->UsesTrack(esdTrack->GetID())) continue;
\r
1293 esdTrack->GetPxPyPz(p);
\r
1294 esdTrack->GetXYZ(pos);
\r
1295 esdTrack->GetCovarianceXYZPxPyPz(covTr);
\r
1296 esdTrack->GetESDpid(pid);
\r
1297 if(fMChandler)fMChandler->SelectParticle(esdTrack->GetLabel());
\r
1298 fPrimaryVertex->AddDaughter(aodTrack =
\r
1299 new(Tracks()[fNumberOfTracks++]) AliAODTrack(esdTrack->GetID(),
\r
1300 esdTrack->GetLabel(),
\r
1306 (Short_t)esdTrack->GetSign(),
\r
1307 esdTrack->GetITSClusterMap(),
\r
1310 kTRUE, // check if this is right
\r
1311 vtx->UsesTrack(esdTrack->GetID()),
\r
1312 AliAODTrack::kPrimary,
\r
1315 aodTrack->SetTPCClusterMap(esdTrack->GetTPCClusterMap());
\r
1316 aodTrack->SetTPCSharedMap (esdTrack->GetTPCSharedMap());
\r
1317 aodTrack->SetChi2perNDF(Chi2perNDF(esdTrack));
\r
1318 aodTrack->SetTPCPointsF(esdTrack->GetTPCNclsF());
\r
1319 if(esdTrack->IsEMCAL()) aodTrack->SetEMCALcluster(esdTrack->GetEMCALcluster());
\r
1320 if(esdTrack->IsPHOS()) aodTrack->SetPHOScluster(esdTrack->GetPHOScluster());
\r
1322 fAODTrackRefs->AddAt(aodTrack, nTrack);
\r
1325 if (esdTrack->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
1326 aodTrack->SetFlags(esdTrack->GetStatus());
\r
1327 aodTrack->ConvertAliPIDtoAODPID();
\r
1328 SetAODPID(esdTrack,aodTrack,detpid);
\r
1329 } // end of loop on tracks
\r
1332 //______________________________________________________________________________
\r
1333 void AliAnalysisTaskESDfilter::ConvertPmdClusters(const AliESDEvent& esd)
\r
1335 AliCodeTimerAuto("",0);
\r
1336 Int_t jPmdClusters=0;
\r
1337 // Access to the AOD container of PMD clusters
\r
1338 TClonesArray &pmdClusters = *(AODEvent()->GetPmdClusters());
\r
1339 for (Int_t iPmd = 0; iPmd < esd.GetNumberOfPmdTracks(); ++iPmd) {
\r
1340 // file pmd clusters, to be revised!
\r
1341 AliESDPmdTrack *pmdTrack = esd.GetPmdTrack(iPmd);
\r
1343 Int_t *label = 0x0;
\r
1344 Double_t posPmd[3] = { pmdTrack->GetClusterX(), pmdTrack->GetClusterY(), pmdTrack->GetClusterZ()};
\r
1345 Double_t pidPmd[13] = { 0.}; // to be revised!
\r
1347 // assoc cluster not set
\r
1348 new(pmdClusters[jPmdClusters++]) AliAODPmdCluster(iPmd, nLabel, label, pmdTrack->GetClusterADC(), posPmd, pidPmd);
\r
1352 //______________________________________________________________________________
\r
1353 void AliAnalysisTaskESDfilter::ConvertCaloClusters(const AliESDEvent& esd)
\r
1355 AliCodeTimerAuto("",0);
\r
1357 // Access to the AOD container of clusters
\r
1358 TClonesArray &caloClusters = *(AODEvent()->GetCaloClusters());
\r
1359 Int_t jClusters(0);
\r
1361 for (Int_t iClust=0; iClust<esd.GetNumberOfCaloClusters(); ++iClust) {
\r
1363 AliESDCaloCluster * cluster = esd.GetCaloCluster(iClust);
\r
1365 Int_t id = cluster->GetID();
\r
1366 Int_t nLabel = cluster->GetNLabels();
\r
1367 Int_t *labels = cluster->GetLabels();
\r
1369 for(int i = 0;i < nLabel;++i){
\r
1370 if(fMChandler)fMChandler->SelectParticle(labels[i]);
\r
1374 Float_t energy = cluster->E();
\r
1375 Float_t posF[3] = { 0.};
\r
1376 cluster->GetPosition(posF);
\r
1378 AliAODCaloCluster *caloCluster = new(caloClusters[jClusters++]) AliAODCaloCluster(id,
\r
1384 cluster->GetType(),0);
\r
1386 caloCluster->SetCaloCluster(cluster->GetDistanceToBadChannel(),
\r
1387 cluster->GetDispersion(),
\r
1388 cluster->GetM20(), cluster->GetM02(),
\r
1389 cluster->GetEmcCpvDistance(),
\r
1390 cluster->GetNExMax(),cluster->GetTOF()) ;
\r
1392 caloCluster->SetPIDFromESD(cluster->GetPID());
\r
1393 caloCluster->SetNCells(cluster->GetNCells());
\r
1394 caloCluster->SetCellsAbsId(cluster->GetCellsAbsId());
\r
1395 caloCluster->SetCellsAmplitudeFraction(cluster->GetCellsAmplitudeFraction());
\r
1397 caloCluster->SetTrackDistance(cluster->GetTrackDx(), cluster->GetTrackDz());
\r
1399 TArrayI* matchedT = cluster->GetTracksMatched();
\r
1400 if (fNumberOfTracks>0 && matchedT && cluster->GetTrackMatchedIndex() >= 0) {
\r
1401 for (Int_t im = 0; im < matchedT->GetSize(); im++) {
\r
1402 Int_t iESDtrack = matchedT->At(im);;
\r
1403 if (fAODTrackRefs->At(iESDtrack) != 0) {
\r
1404 caloCluster->AddTrackMatched((AliAODTrack*)fAODTrackRefs->At(iESDtrack));
\r
1410 caloClusters.Expand(jClusters); // resize TObjArray to 'remove' slots for pseudo clusters
\r
1413 //______________________________________________________________________________
\r
1414 void AliAnalysisTaskESDfilter::ConvertEMCALCells(const AliESDEvent& esd)
\r
1416 AliCodeTimerAuto("",0);
\r
1417 // fill EMCAL cell info
\r
1418 if (esd.GetEMCALCells()) { // protection against missing ESD information
\r
1419 AliESDCaloCells &esdEMcells = *(esd.GetEMCALCells());
\r
1420 Int_t nEMcell = esdEMcells.GetNumberOfCells() ;
\r
1422 AliAODCaloCells &aodEMcells = *(AODEvent()->GetEMCALCells());
\r
1423 aodEMcells.CreateContainer(nEMcell);
\r
1424 aodEMcells.SetType(AliAODCaloCells::kEMCALCell);
\r
1425 for (Int_t iCell = 0; iCell < nEMcell; iCell++) {
\r
1426 aodEMcells.SetCell(iCell,esdEMcells.GetCellNumber(iCell),esdEMcells.GetAmplitude(iCell));
\r
1428 aodEMcells.Sort();
\r
1432 //______________________________________________________________________________
\r
1433 void AliAnalysisTaskESDfilter::ConvertPHOSCells(const AliESDEvent& esd)
\r
1435 AliCodeTimerAuto("",0);
\r
1436 // fill PHOS cell info
\r
1437 if (esd.GetPHOSCells()) { // protection against missing ESD information
\r
1438 AliESDCaloCells &esdPHcells = *(esd.GetPHOSCells());
\r
1439 Int_t nPHcell = esdPHcells.GetNumberOfCells() ;
\r
1441 AliAODCaloCells &aodPHcells = *(AODEvent()->GetPHOSCells());
\r
1442 aodPHcells.CreateContainer(nPHcell);
\r
1443 aodPHcells.SetType(AliAODCaloCells::kPHOSCell);
\r
1444 for (Int_t iCell = 0; iCell < nPHcell; iCell++) {
\r
1445 aodPHcells.SetCell(iCell,esdPHcells.GetCellNumber(iCell),esdPHcells.GetAmplitude(iCell));
\r
1447 aodPHcells.Sort();
\r
1451 //______________________________________________________________________________
\r
1452 void AliAnalysisTaskESDfilter::ConvertTracklets(const AliESDEvent& esd)
\r
1455 AliCodeTimerAuto("",0);
\r
1457 AliAODTracklets &SPDTracklets = *(AODEvent()->GetTracklets());
\r
1458 const AliMultiplicity *mult = esd.GetMultiplicity();
\r
1460 if (mult->GetNumberOfTracklets()>0) {
\r
1461 SPDTracklets.CreateContainer(mult->GetNumberOfTracklets());
\r
1463 for (Int_t n=0; n<mult->GetNumberOfTracklets(); n++) {
\r
1465 fMChandler->SelectParticle(mult->GetLabel(n, 0));
\r
1466 fMChandler->SelectParticle(mult->GetLabel(n, 1));
\r
1468 SPDTracklets.SetTracklet(n, mult->GetTheta(n), mult->GetPhi(n), mult->GetDeltaPhi(n), mult->GetLabel(n, 0),mult->GetLabel(n, 1));
\r
1472 //Printf("ERROR: AliMultiplicity could not be retrieved from ESD");
\r
1476 //______________________________________________________________________________
\r
1477 void AliAnalysisTaskESDfilter::ConvertKinks(const AliESDEvent& esd)
\r
1479 AliCodeTimerAuto("",0);
\r
1481 // Kinks: it is a big mess the access to the information in the kinks
\r
1482 // The loop is on the tracks in order to find the mother and daugther of each kink
\r
1484 Double_t covTr[21]={0.};
\r
1485 Double_t pid[10]={0.};
\r
1486 AliAODPid* detpid(0x0);
\r
1488 fNumberOfKinks = esd.GetNumberOfKinks();
\r
1490 const AliESDVertex* vtx = esd.GetPrimaryVertex();
\r
1492 for (Int_t iTrack=0; iTrack<esd.GetNumberOfTracks(); ++iTrack)
\r
1494 AliESDtrack * esdTrack = esd.GetTrack(iTrack);
\r
1496 Int_t ikink = esdTrack->GetKinkIndex(0);
\r
1498 if (ikink && fNumberOfKinks) {
\r
1499 // Negative kink index: mother, positive: daughter
\r
1501 // Search for the second track of the kink
\r
1503 for (Int_t jTrack = iTrack+1; jTrack<esd.GetNumberOfTracks(); ++jTrack) {
\r
1505 AliESDtrack * esdTrack1 = esd.GetTrack(jTrack);
\r
1507 Int_t jkink = esdTrack1->GetKinkIndex(0);
\r
1509 if ( TMath::Abs(ikink)==TMath::Abs(jkink) ) {
\r
1511 // The two tracks are from the same kink
\r
1513 if (fUsedKink[TMath::Abs(ikink)-1]) continue; // skip used kinks
\r
1515 Int_t imother = -1;
\r
1516 Int_t idaughter = -1;
\r
1518 if (ikink<0 && jkink>0) {
\r
1521 idaughter = jTrack;
\r
1523 else if (ikink>0 && jkink<0) {
\r
1526 idaughter = iTrack;
\r
1529 // cerr << "Error: Wrong combination of kink indexes: "
\r
1530 // << ikink << " " << jkink << endl;
\r
1534 // Add the mother track if it passed primary track selection cuts
\r
1536 AliAODTrack * mother = NULL;
\r
1538 UInt_t selectInfo = 0;
\r
1539 if (fTrackFilter) {
\r
1540 selectInfo = fTrackFilter->IsSelected(esd.GetTrack(imother));
\r
1541 if (!selectInfo) continue;
\r
1544 if (!fUsedTrack[imother]) {
\r
1546 fUsedTrack[imother] = kTRUE;
\r
1548 AliESDtrack *esdTrackM = esd.GetTrack(imother);
\r
1549 Double_t p[3] = { 0. };
\r
1550 Double_t pos[3] = { 0. };
\r
1551 esdTrackM->GetPxPyPz(p);
\r
1552 esdTrackM->GetXYZ(pos);
\r
1553 esdTrackM->GetCovarianceXYZPxPyPz(covTr);
\r
1554 esdTrackM->GetESDpid(pid);
\r
1555 if(fMChandler)fMChandler->SelectParticle(esdTrackM->GetLabel());
\r
1557 new(Tracks()[fNumberOfTracks++]) AliAODTrack(esdTrackM->GetID(),
\r
1558 esdTrackM->GetLabel(),
\r
1564 (Short_t)esdTrackM->GetSign(),
\r
1565 esdTrackM->GetITSClusterMap(),
\r
1568 kTRUE, // check if this is right
\r
1569 vtx->UsesTrack(esdTrack->GetID()),
\r
1570 AliAODTrack::kPrimary,
\r
1572 mother->SetTPCClusterMap(esdTrackM->GetTPCClusterMap());
\r
1573 mother->SetTPCSharedMap (esdTrackM->GetTPCSharedMap());
\r
1574 mother->SetChi2perNDF(Chi2perNDF(esdTrackM));
\r
1575 mother->SetTPCPointsF(esdTrackM->GetTPCNclsF());
\r
1577 fAODTrackRefs->AddAt(mother, imother);
\r
1579 if (esdTrackM->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
1580 mother->SetFlags(esdTrackM->GetStatus());
\r
1581 mother->ConvertAliPIDtoAODPID();
\r
1582 fPrimaryVertex->AddDaughter(mother);
\r
1583 mother->ConvertAliPIDtoAODPID();
\r
1584 SetAODPID(esdTrackM,mother,detpid);
\r
1587 // cerr << "Error: event " << esd.GetEventNumberInFile() << " kink " << TMath::Abs(ikink)-1
\r
1588 // << " track " << imother << " has already been used!" << endl;
\r
1591 // Add the kink vertex
\r
1592 AliESDkink * kink = esd.GetKink(TMath::Abs(ikink)-1);
\r
1594 AliAODVertex * vkink =
\r
1595 new(Vertices()[fNumberOfVertices++]) AliAODVertex(kink->GetPosition(),
\r
1599 esdTrack->GetID(), // This is the track ID of the mother's track!
\r
1600 AliAODVertex::kKink);
\r
1601 // Add the daughter track
\r
1603 AliAODTrack * daughter = NULL;
\r
1605 if (!fUsedTrack[idaughter]) {
\r
1607 fUsedTrack[idaughter] = kTRUE;
\r
1609 AliESDtrack *esdTrackD = esd.GetTrack(idaughter);
\r
1610 Double_t p[3] = { 0. };
\r
1611 Double_t pos[3] = { 0. };
\r
1613 esdTrackD->GetPxPyPz(p);
\r
1614 esdTrackD->GetXYZ(pos);
\r
1615 esdTrackD->GetCovarianceXYZPxPyPz(covTr);
\r
1616 esdTrackD->GetESDpid(pid);
\r
1618 if (fTrackFilter) selectInfo = fTrackFilter->IsSelected(esdTrackD);
\r
1619 if(fMChandler)fMChandler->SelectParticle(esdTrackD->GetLabel());
\r
1621 new(Tracks()[fNumberOfTracks++]) AliAODTrack(esdTrackD->GetID(),
\r
1622 esdTrackD->GetLabel(),
\r
1628 (Short_t)esdTrackD->GetSign(),
\r
1629 esdTrackD->GetITSClusterMap(),
\r
1632 kTRUE, // check if this is right
\r
1633 vtx->UsesTrack(esdTrack->GetID()),
\r
1634 AliAODTrack::kSecondary,
\r
1636 daughter->SetTPCClusterMap(esdTrackD->GetTPCClusterMap());
\r
1637 daughter->SetTPCSharedMap (esdTrackD->GetTPCSharedMap());
\r
1638 daughter->SetTPCPointsF(esdTrackD->GetTPCNclsF());
\r
1639 fAODTrackRefs->AddAt(daughter, idaughter);
\r
1641 if (esdTrackD->GetSign() > 0) ++fNumberOfPositiveTracks;
\r
1642 daughter->SetFlags(esdTrackD->GetStatus());
\r
1643 daughter->ConvertAliPIDtoAODPID();
\r
1644 vkink->AddDaughter(daughter);
\r
1645 daughter->ConvertAliPIDtoAODPID();
\r
1646 SetAODPID(esdTrackD,daughter,detpid);
\r
1649 // cerr << "Error: event " << esd.GetEventNumberInFile() << " kink " << TMath::Abs(ikink)-1
\r
1650 // << " track " << idaughter << " has already been used!" << endl;
\r
1658 //______________________________________________________________________________
\r
1659 void AliAnalysisTaskESDfilter::ConvertPrimaryVertices(const AliESDEvent& esd)
\r
1661 AliCodeTimerAuto("",0);
\r
1663 // Access to the AOD container of vertices
\r
1664 fNumberOfVertices = 0;
\r
1666 Double_t pos[3] = { 0. };
\r
1667 Double_t covVtx[6] = { 0. };
\r
1669 // Add primary vertex. The primary tracks will be defined
\r
1670 // after the loops on the composite objects (V0, cascades, kinks)
\r
1671 const AliESDVertex *vtx = esd.GetPrimaryVertex();
\r
1673 vtx->GetXYZ(pos); // position
\r
1674 vtx->GetCovMatrix(covVtx); //covariance matrix
\r
1676 fPrimaryVertex = new(Vertices()[fNumberOfVertices++])
\r
1677 AliAODVertex(pos, covVtx, vtx->GetChi2toNDF(), NULL, -1, AliAODVertex::kPrimary);
\r
1678 fPrimaryVertex->SetName(vtx->GetName());
\r
1679 fPrimaryVertex->SetTitle(vtx->GetTitle());
\r
1681 TString vtitle = vtx->GetTitle();
\r
1682 if (!vtitle.Contains("VertexerTracks"))
\r
1683 fPrimaryVertex->SetNContributors(vtx->GetNContributors());
\r
1685 if (fDebug > 0) fPrimaryVertex->Print();
\r
1687 // Add SPD "main" vertex
\r
1688 const AliESDVertex *vtxS = esd.GetPrimaryVertexSPD();
\r
1689 vtxS->GetXYZ(pos); // position
\r
1690 vtxS->GetCovMatrix(covVtx); //covariance matrix
\r
1691 AliAODVertex * mVSPD = new(Vertices()[fNumberOfVertices++])
\r
1692 AliAODVertex(pos, covVtx, vtxS->GetChi2toNDF(), NULL, -1, AliAODVertex::kMainSPD);
\r
1693 mVSPD->SetName(vtxS->GetName());
\r
1694 mVSPD->SetTitle(vtxS->GetTitle());
\r
1695 mVSPD->SetNContributors(vtxS->GetNContributors());
\r
1697 // Add SPD pileup vertices
\r
1698 for(Int_t iV=0; iV<esd.GetNumberOfPileupVerticesSPD(); ++iV)
\r
1700 const AliESDVertex *vtxP = esd.GetPileupVertexSPD(iV);
\r
1701 vtxP->GetXYZ(pos); // position
\r
1702 vtxP->GetCovMatrix(covVtx); //covariance matrix
\r
1703 AliAODVertex * pVSPD = new(Vertices()[fNumberOfVertices++])
\r
1704 AliAODVertex(pos, covVtx, vtxP->GetChi2toNDF(), NULL, -1, AliAODVertex::kPileupSPD);
\r
1705 pVSPD->SetName(vtxP->GetName());
\r
1706 pVSPD->SetTitle(vtxP->GetTitle());
\r
1707 pVSPD->SetNContributors(vtxP->GetNContributors());
\r
1708 pVSPD->SetBC(vtxP->GetBC());
\r
1711 // Add TRK pileup vertices
\r
1712 for(Int_t iV=0; iV<esd.GetNumberOfPileupVerticesTracks(); ++iV)
\r
1714 const AliESDVertex *vtxP = esd.GetPileupVertexTracks(iV);
\r
1715 vtxP->GetXYZ(pos); // position
\r
1716 vtxP->GetCovMatrix(covVtx); //covariance matrix
\r
1717 AliAODVertex * pVTRK = new(Vertices()[fNumberOfVertices++])
\r
1718 AliAODVertex(pos, covVtx, vtxP->GetChi2toNDF(), NULL, -1, AliAODVertex::kPileupTracks);
\r
1719 pVTRK->SetName(vtxP->GetName());
\r
1720 pVTRK->SetTitle(vtxP->GetTitle());
\r
1721 pVTRK->SetNContributors(vtxP->GetNContributors());
\r
1722 pVTRK->SetBC(vtxP->GetBC());
\r
1726 //______________________________________________________________________________
\r
1727 void AliAnalysisTaskESDfilter::ConvertVZERO(const AliESDEvent& esd)
\r
1729 // Convert VZERO data
\r
1730 AliAODVZERO* vzeroData = AODEvent()->GetVZEROData();
\r
1731 *vzeroData = *(esd.GetVZEROData());
\r
1734 //______________________________________________________________________________
\r
1735 void AliAnalysisTaskESDfilter::ConvertZDC(const AliESDEvent& esd)
\r
1737 // Convert ZDC data
\r
1738 AliESDZDC* esdZDC = esd.GetZDCData();
\r
1740 const Double_t zem1Energy = esdZDC->GetZEM1Energy();
\r
1741 const Double_t zem2Energy = esdZDC->GetZEM2Energy();
\r
1743 const Double_t *towZNC = esdZDC->GetZNCTowerEnergy();
\r
1744 const Double_t *towZPC = esdZDC->GetZPCTowerEnergy();
\r
1745 const Double_t *towZNA = esdZDC->GetZNATowerEnergy();
\r
1746 const Double_t *towZPA = esdZDC->GetZPATowerEnergy();
\r
1747 const Double_t *towZNCLG = esdZDC->GetZNCTowerEnergyLR();
\r
1748 const Double_t *towZNALG = esdZDC->GetZNATowerEnergyLR();
\r
1750 AliAODZDC* zdcAOD = AODEvent()->GetZDCData();
\r
1752 zdcAOD->SetZEM1Energy(zem1Energy);
\r
1753 zdcAOD->SetZEM2Energy(zem2Energy);
\r
1754 zdcAOD->SetZNCTowers(towZNC, towZNCLG);
\r
1755 zdcAOD->SetZNATowers(towZNA, towZNALG);
\r
1756 zdcAOD->SetZPCTowers(towZPC);
\r
1757 zdcAOD->SetZPATowers(towZPA);
\r
1759 zdcAOD->SetZDCParticipants(esdZDC->GetZDCParticipants(), esdZDC->GetZDCPartSideA(), esdZDC->GetZDCPartSideC());
\r
1760 zdcAOD->SetZDCImpactParameter(esdZDC->GetImpactParameter(), esdZDC->GetImpactParamSideA(),
\r
1761 esdZDC->GetImpactParamSideC());
\r
1762 zdcAOD->SetZDCTDCSum(esdZDC->GetZNTDCSum(0));
\r
1763 zdcAOD->SetZDCTDCDiff(esdZDC->GetZNTDCDiff(0));
\r
1767 //______________________________________________________________________________
\r
1768 void AliAnalysisTaskESDfilter::ConvertESDtoAOD()
\r
1770 // ESD Filter analysis task executed for each event
\r
1772 AliESDEvent* esd = dynamic_cast<AliESDEvent*>(InputEvent());
\r
1776 AliCodeTimerAuto("",0);
\r
1778 fOldESDformat = ( esd->GetAliESDOld() != 0x0 );
\r
1780 fNumberOfTracks = 0;
\r
1781 fNumberOfPositiveTracks = 0;
\r
1783 fNumberOfVertices = 0;
\r
1784 fNumberOfCascades = 0;
\r
1785 fNumberOfKinks = 0;
\r
1787 AliAODHeader* header = ConvertHeader(*esd);
\r
1789 if ( fIsVZEROEnabled ) ConvertVZERO(*esd);
\r
1791 // Fetch Stack for debuggging if available
\r
1795 fMChandler = (AliMCEventHandler*) ((AliAnalysisManager::GetAnalysisManager())->GetMCtruthEventHandler());
\r
1798 // loop over events and fill them
\r
1799 // Multiplicity information needed by the header (to be revised!)
\r
1800 Int_t nTracks = esd->GetNumberOfTracks();
\r
1801 for (Int_t iTrack=0; iTrack<nTracks; ++iTrack) esd->GetTrack(iTrack)->SetESDEvent(esd);
\r
1803 // Update the header
\r
1805 Int_t nV0s = esd->GetNumberOfV0s();
\r
1806 Int_t nCascades = esd->GetNumberOfCascades();
\r
1807 Int_t nKinks = esd->GetNumberOfKinks();
\r
1808 Int_t nVertices = nV0s + nCascades /*V0 wihtin cascade already counted*/+ nKinks + 1 /* = prim. vtx*/;
\r
1809 Int_t nPileSPDVertices=1+esd->GetNumberOfPileupVerticesSPD(); // also SPD main vertex
\r
1810 Int_t nPileTrkVertices=esd->GetNumberOfPileupVerticesTracks();
\r
1811 nVertices+=nPileSPDVertices;
\r
1812 nVertices+=nPileTrkVertices;
\r
1814 Int_t nCaloClus = esd->GetNumberOfCaloClusters();
\r
1815 Int_t nFmdClus = 0;
\r
1816 Int_t nPmdClus = esd->GetNumberOfPmdTracks();
\r
1818 AliDebug(1,Form(" NV0=%d NCASCADES=%d NKINKS=%d", nV0s, nCascades, nKinks));
\r
1820 AODEvent()->ResetStd(nTracks, nVertices, nV0s, nCascades, nJets, nCaloClus, nFmdClus, nPmdClus);
\r
1824 // RefArray to store a mapping between esd V0 number and newly created AOD-Vertex V0
\r
1825 fAODV0VtxRefs = new TRefArray(nV0s);
\r
1826 // RefArray to store the mapping between esd V0 number and newly created AOD-V0
\r
1827 fAODV0Refs = new TRefArray(nV0s);
\r
1828 // Array to take into account the V0s already added to the AOD (V0 within cascades)
\r
1829 fUsedV0 = new Bool_t[nV0s];
\r
1830 for (Int_t iV0=0; iV0<nV0s; ++iV0) fUsedV0[iV0]=kFALSE;
\r
1835 // RefArray to store the mapping between esd track number and newly created AOD-Track
\r
1837 fAODTrackRefs = new TRefArray(nTracks);
\r
1839 // Array to take into account the tracks already added to the AOD
\r
1840 fUsedTrack = new Bool_t[nTracks];
\r
1841 for (Int_t iTrack=0; iTrack<nTracks; ++iTrack) fUsedTrack[iTrack]=kFALSE;
\r
1844 // Array to take into account the kinks already added to the AOD
\r
1847 fUsedKink = new Bool_t[nKinks];
\r
1848 for (Int_t iKink=0; iKink<nKinks; ++iKink) fUsedKink[iKink]=kFALSE;
\r
1851 ConvertPrimaryVertices(*esd);
\r
1853 //setting best TOF PID
\r
1854 AliESDInputHandler* esdH = dynamic_cast<AliESDInputHandler*>(AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler());
\r
1856 fESDpid = esdH->GetESDpid();
\r
1858 if (fIsPidOwner && fESDpid){
\r
1863 { //in case of no Tender attached
\r
1864 fESDpid = new AliESDpid;
\r
1865 fIsPidOwner = kTRUE;
\r
1868 if(!esd->GetTOFHeader())
\r
1869 { //protection in case the pass2 LHC10b,c,d have been processed without tender.
\r
1870 Float_t t0spread[10];
\r
1871 Float_t intrinsicTOFres=100; //ps ok for LHC10b,c,d pass2!!
\r
1872 for (Int_t i=0; i<10; i++) t0spread[i] = (TMath::Sqrt(esd->GetSigma2DiamondZ()))/0.03; //0.03 to convert from cm to ps
\r
1873 fESDpid->GetTOFResponse().SetT0resolution(t0spread);
\r
1874 fESDpid->GetTOFResponse().SetTimeResolution(intrinsicTOFres);
\r
1876 fESDpid->SetTOFResponse(esd, (AliESDpid::EStartTimeType_t)fTimeZeroType);
\r
1879 if(esd->GetTOFHeader() && fIsPidOwner) fESDpid->SetTOFResponse(esd, (AliESDpid::EStartTimeType_t)fTimeZeroType); //in case of AOD production strating form LHC10e without Tender.
\r
1881 if ( fAreCascadesEnabled ) ConvertCascades(*esd);
\r
1883 if ( fAreV0sEnabled ) ConvertV0s(*esd);
\r
1885 if ( fAreKinksEnabled ) ConvertKinks(*esd);
\r
1887 if ( fAreTracksEnabled ) ConvertTracks(*esd);
\r
1889 // Update number of AOD tracks in header at the end of track loop (M.G.)
\r
1890 header->SetRefMultiplicity(fNumberOfTracks);
\r
1891 header->SetRefMultiplicityPos(fNumberOfPositiveTracks);
\r
1892 header->SetRefMultiplicityNeg(fNumberOfTracks - fNumberOfPositiveTracks);
\r
1894 if ( fTPCConstrainedFilterMask ) ConvertTPCOnlyTracks(*esd);
\r
1895 if( fGlobalConstrainedFilterMask) ConvertGlobalConstrainedTracks(*esd);
\r
1897 if ( fArePmdClustersEnabled ) ConvertPmdClusters(*esd);
\r
1899 if ( fAreCaloClustersEnabled ) ConvertCaloClusters(*esd);
\r
1901 if ( fAreEMCALCellsEnabled )ConvertEMCALCells(*esd);
\r
1903 if ( fArePHOSCellsEnabled )ConvertPHOSCells(*esd);
\r
1905 if ( fAreTrackletsEnabled ) ConvertTracklets(*esd);
\r
1907 delete fAODTrackRefs; fAODTrackRefs=0x0;
\r
1908 delete fAODV0VtxRefs; fAODV0VtxRefs=0x0;
\r
1909 delete fAODV0Refs; fAODV0Refs=0x0;
\r
1911 delete[] fUsedTrack; fUsedTrack=0x0;
\r
1912 delete[] fUsedV0; fUsedV0=0x0;
\r
1913 delete[] fUsedKink; fUsedKink=0x0;
\r
1915 if ( fIsPidOwner){
\r
1924 //______________________________________________________________________________
\r
1925 void AliAnalysisTaskESDfilter::SetAODPID(AliESDtrack *esdtrack, AliAODTrack *aodtrack, AliAODPid *detpid)
\r
1928 // Setter for the raw PID detector signals
\r
1931 // Save PID object for candidate electrons
\r
1932 Bool_t pidSave = kFALSE;
\r
1933 if (fTrackFilter) {
\r
1934 Bool_t selectInfo = fTrackFilter->IsSelected((char*) "Electrons");
\r
1935 if (selectInfo) pidSave = kTRUE;
\r
1939 // Tracks passing pt cut
\r
1940 if(esdtrack->Pt()>fHighPthreshold) {
\r
1944 if(esdtrack->Pt()> fPtshape->GetXmin()){
\r
1945 Double_t y = fPtshape->Eval(esdtrack->Pt())/fPtshape->Eval(fHighPthreshold);
\r
1946 if(gRandom->Rndm(0)<1./y){
\r
1949 }//end if p < pmin
\r
1950 }//end if p function
\r
1954 if(!aodtrack->GetDetPid()){// prevent memory leak when calling SetAODPID twice for the same track
\r
1955 detpid = new AliAODPid();
\r
1956 SetDetectorRawSignals(detpid,esdtrack);
\r
1957 aodtrack->SetDetPID(detpid);
\r
1962 //______________________________________________________________________________
\r
1963 void AliAnalysisTaskESDfilter::SetDetectorRawSignals(AliAODPid *aodpid, AliESDtrack *track)
\r
1966 //assignment of the detector signals (AliXXXesdPID inspired)
\r
1969 AliInfo("no ESD track found. .....exiting");
\r
1973 const AliExternalTrackParam *in=track->GetInnerParam();
\r
1975 aodpid->SetTPCmomentum(in->GetP());
\r
1977 aodpid->SetTPCmomentum(-1.);
\r
1981 aodpid->SetITSsignal(track->GetITSsignal());
\r
1982 Double_t itsdedx[4]; // dE/dx samples for individual ITS layers
\r
1983 track->GetITSdEdxSamples(itsdedx);
\r
1984 aodpid->SetITSdEdxSamples(itsdedx);
\r
1986 aodpid->SetTPCsignal(track->GetTPCsignal());
\r
1987 aodpid->SetTPCsignalN(track->GetTPCsignalN());
\r
1989 //n TRD planes = 6
\r
1990 Int_t nslices = track->GetNumberOfTRDslices()*6;
\r
1991 TArrayD trdslices(nslices);
\r
1992 for(Int_t iSl =0; iSl < track->GetNumberOfTRDslices(); iSl++) {
\r
1993 for(Int_t iPl =0; iPl<6; iPl++) trdslices[iPl*track->GetNumberOfTRDslices()+iSl] = track->GetTRDslice(iPl,iSl);
\r
1997 for(Int_t iPl=0;iPl<6;iPl++){
\r
1998 Double_t trdmom=track->GetTRDmomentum(iPl);
\r
1999 aodpid->SetTRDmomentum(iPl,trdmom);
\r
2002 aodpid->SetTRDsignal(track->GetNumberOfTRDslices()*6,trdslices.GetArray());
\r
2004 //TRD clusters and tracklets
\r
2005 aodpid->SetTRDncls(track->GetTRDncls());
\r
2006 aodpid->SetTRDntrackletsPID(track->GetTRDntrackletsPID());
\r
2009 Double_t times[AliAODPid::kSPECIES]; track->GetIntegratedTimes(times);
\r
2010 aodpid->SetIntegratedTimes(times);
\r
2012 Float_t tzeroTrack = fESDpid->GetTOFResponse().GetStartTime(track->P());
\r
2013 aodpid->SetTOFsignal(track->GetTOFsignal()-tzeroTrack);
\r
2015 Double_t tofRes[5];
\r
2016 for (Int_t iMass=0; iMass<5; iMass++){
\r
2017 tofRes[iMass]=(Double_t)fESDpid->GetTOFResponse().GetExpectedSigma(track->P(), times[iMass], AliPID::ParticleMass(iMass));
\r
2019 aodpid->SetTOFpidResolution(tofRes);
\r
2021 aodpid->SetHMPIDsignal(track->GetHMPIDsignal());
\r
2023 //Extrapolate track to EMCAL surface for AOD-level track-cluster matching
\r
2024 Double_t emcpos[3] = {0.,0.,0.};
\r
2025 Double_t emcmom[3] = {0.,0.,0.};
\r
2026 aodpid->SetEMCALPosition(emcpos);
\r
2027 aodpid->SetEMCALMomentum(emcmom);
\r
2029 Double_t hmpPid[5] = {0};
\r
2030 track->GetHMPIDpid(hmpPid);
\r
2031 aodpid->SetHMPIDprobs(hmpPid);
\r
2033 AliExternalTrackParam *outerparam = (AliExternalTrackParam*)track->GetOuterParam();
\r
2034 if(!outerparam) return;
\r
2036 //To be replaced by call to AliEMCALGeoUtils when the class becomes available
\r
2037 Bool_t okpos = outerparam->GetXYZ(emcpos);
\r
2038 Bool_t okmom = outerparam->GetPxPyPz(emcmom);
\r
2039 if(!(okpos && okmom)) return;
\r
2041 aodpid->SetEMCALPosition(emcpos);
\r
2042 aodpid->SetEMCALMomentum(emcmom);
\r
2046 Double_t AliAnalysisTaskESDfilter::Chi2perNDF(AliESDtrack* track)
\r
2048 // Calculate chi2 per ndf for track
\r
2049 Int_t nClustersTPC = track->GetTPCNcls();
\r
2051 if ( nClustersTPC > 5) {
\r
2052 return (track->GetTPCchi2()/Float_t(nClustersTPC - 5));
\r
2059 //______________________________________________________________________________
\r
2060 void AliAnalysisTaskESDfilter::Terminate(Option_t */*option*/)
\r
2062 // Terminate analysis
\r
2064 if (fDebug > 1) printf("AnalysisESDfilter: Terminate() \n");
\r
2067 //______________________________________________________________________________
\r
2068 void AliAnalysisTaskESDfilter::PrintMCInfo(AliStack *pStack,Int_t label){
\r
2070 if(!pStack)return;
\r
2071 label = TMath::Abs(label);
\r
2072 TParticle *part = pStack->Particle(label);
\r
2073 Printf("########################");
\r
2074 Printf("%s:%d %d UniqueID %d PDG %d P %3.3f",(char*)__FILE__,__LINE__,label,part->GetUniqueID(),part->GetPdgCode(),part->P());
\r
2076 TParticle* mother = part;
\r
2077 Int_t imo = part->GetFirstMother();
\r
2078 Int_t nprim = pStack->GetNprimary();
\r
2079 // while((imo >= nprim) && (mother->GetUniqueID() == 4)) {
\r
2080 while((imo >= nprim)) {
\r
2081 mother = pStack->Particle(imo);
\r
2082 Printf("Mother %s:%d Label %d UniqueID %d PDG %d P %3.3f",(char*)__FILE__,__LINE__,imo,mother->GetUniqueID(),mother->GetPdgCode(),mother->P());
\r
2084 imo = mother->GetFirstMother();
\r
2086 Printf("########################");
\r