1 #if !defined(__CINT__) || defined(__MAKECINT__)
8 #include "AliAODEvent.h"
9 #include "AliAODVertex.h"
10 #include "AliAODTrack.h"
11 #include "AliAODCluster.h"
14 #include "AliESDtrack.h"
15 #include "AliESDVertex.h"
17 #include "AliESDCascade.h"
18 #include "AliESDCaloCluster.h"
22 void CreateAODfromESD(const char *inFileName = "AliESDs.root",
23 const char *outFileName = "AliAOD.root") {
25 // create an AliAOD object
26 AliAODEvent *aod = new AliAODEvent();
27 aod->CreateStdContent();
30 TFile *outFile = TFile::Open(outFileName, "RECREATE");
33 TTree *aodTree = new TTree("AOD", "AliAOD tree");
34 aodTree->Branch(aod->GetList());
37 TFile *inFile = TFile::Open(inFileName, "READ");
38 TTree *t = (TTree*) inFile->Get("esdTree");
39 TBranch *b = t->GetBranch("ESD");
43 Int_t nEvents = b->GetEntries();
45 // loop over events and fill them
46 for (Int_t iEvent = 0; iEvent < nEvents; ++iEvent) {
49 // Multiplicity information needed by the header (to be revised!)
50 Int_t nTracks = esd->GetNumberOfTracks();
52 for (Int_t iTrack=0; iTrack<nTracks; ++iTrack)
53 if (esd->GetTrack(iTrack)->GetSign()> 0) nPosTracks++;
56 aod->AddHeader(new AliAODHeader(esd ->GetEventNumber(),
61 esd->GetMagneticField(),
62 -999., // centrality; to be filled, still
63 esd->GetTriggerMask(),
64 esd->GetTriggerCluster(),
65 esd->GetEventType()));
67 Int_t nV0s = esd->GetNumberOfV0s();
68 Int_t nCascades = esd->GetNumberOfCascades();
69 Int_t nKinks = esd->GetNumberOfKinks();
70 Int_t nVertices = nV0s + nCascades + nKinks;
72 aod->ResetStd(nTracks, nVertices);
75 // Array to take into account the tracks already added to the AOD
76 Bool_t * usedTrack = NULL;
78 usedTrack = new Bool_t[nTracks];
79 for (Int_t iTrack=0; iTrack<nTracks; ++iTrack) usedTrack[iTrack]=kFALSE;
81 // Array to take into account the V0s already added to the AOD
82 Bool_t * usedV0 = NULL;
84 usedV0 = new Bool_t[nV0s];
85 for (Int_t iV0=0; iV0<nV0s; ++iV0) usedV0[iV0]=kFALSE;
87 // Array to take into account the kinks already added to the AOD
88 Bool_t * usedKink = NULL;
90 usedKink = new Bool_t[nKinks];
91 for (Int_t iKink=0; iKink<nKinks; ++iKink) usedKink[iKink]=kFALSE;
94 // Access to the AOD container of vertices
95 TClonesArray &vertices = *(aod->GetVertices());
98 // Access to the AOD container of tracks
99 TClonesArray &tracks = *(aod->GetTracks());
102 // Add primary vertex. The primary tracks will be defined
103 // after the loops on the composite objects (V0, cascades, kinks)
104 const AliESDVertex *vtx = esd->GetPrimaryVertex();
107 vtx->GetXYZ(pos); // position
109 vtx->GetCovMatrix(cov); //covariance matrix
111 AliAODVertex * primary = new(vertices[jVertices++])
112 AliAODVertex(pos, cov, vtx->GetChi2(), NULL, AliAODVertex::kPrimary);
114 // Create vertices starting from the most complex objects
117 for (Int_t nCascade = 0; nCascade < nCascades; ++nCascade) {
118 AliESDcascade *cascade = esd->GetCascade(nCascade);
121 cascade->GetXYZ(posXi[0], posXi[1], posXi[2]);
123 cascade->GetPosCovXi(covXi);
125 // Add the cascade vertex
126 AliAODVertex * vcascade = new(vertices[jVertices++]) AliAODVertex(posXi,
128 cascade->GetChi2Xi(),
130 AliAODVertex::kCascade);
132 primary->AddDaughter(vcascade);
134 // Add the V0 from the cascade. The ESD class have to be optimized...
135 // Now we have to search for the corresponding Vo in the list of V0s
136 // using the indeces of the positive and negative tracks
138 Int_t posFromV0 = cascade->GetPindex();
139 Int_t negFromV0 = cascade->GetNindex();
145 for (Int_t iV0=0; iV0<nV0s; ++iV0) {
147 v0 = esd->GetV0(iV0);
148 Int_t pos = v0->GetPindex();
149 Int_t neg = v0->GetNindex();
151 if (pos==posFromV0 && neg==negFromV0) {
157 AliAODVertex * vV0FromCascade = 0x0;
159 if (indV0>-1 && !usedV0[indV0] ) {
161 // the V0 exists in the array of V0s and is not used
163 usedV0[indV0] = kTRUE;
166 v0->GetXYZ(posV0[0], posV0[1], posV0[2]);
168 v0->GetPosCov(covV0);
170 vV0FromCascade = new(vertices[jVertices++]) AliAODVertex(posV0,
177 // the V0 doesn't exist in the array of V0s or was used
178 cerr << "Error: event " << iEvent << " cascade " << nCascade
179 << " The V0 " << indV0
180 << " doesn't exist in the array of V0s or was used!" << endl;
183 cascade->GetXYZ(posV0[0], posV0[1], posV0[2]);
185 cascade->GetPosCov(covV0);
187 vV0FromCascade = new(vertices[jVertices++]) AliAODVertex(posV0,
192 vcascade->AddDaughter(vV0FromCascade);
195 // Add the positive tracks from the V0
197 if (! usedTrack[posFromV0]) {
199 usedTrack[posFromV0] = kTRUE;
201 AliESDtrack *esdTrack = esd->GetTrack(posFromV0);
204 esdTrack->GetPxPyPz(p);
210 esdTrack->GetCovarianceXYZPxPyPz(cov);
213 esdTrack->GetESDpid(pid);
215 vV0FromCascade->AddDaughter(
216 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
217 esdTrack->GetLabel(),
222 (Short_t)esdTrack->GetSign(),
223 esdTrack->GetITSClusterMap(),
226 AliAODTrack::kSecondary)
230 cerr << "Error: event " << iEvent << " cascade " << nCascade
231 << " track " << posFromV0 << " has already been used!" << endl;
234 // Add the negative tracks from the V0
236 if (!usedTrack[negFromV0]) {
238 usedTrack[negFromV0] = kTRUE;
240 AliESDtrack *esdTrack = esd->GetTrack(negFromV0);
243 esdTrack->GetPxPyPz(p);
249 esdTrack->GetCovarianceXYZPxPyPz(cov);
252 esdTrack->GetESDpid(pid);
254 vV0FromCascade->AddDaughter(
255 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
256 esdTrack->GetLabel(),
262 (Short_t)esdTrack->GetSign(),
263 esdTrack->GetITSClusterMap(),
266 AliAODTrack::kSecondary)
270 cerr << "Error: event " << iEvent << " cascade " << nCascade
271 << " track " << negFromV0 << " has already been used!" << endl;
274 // Add the bachelor track from the cascade
276 Int_t bachelor = cascade->GetBindex();
278 if(!usedTrack[bachelor]) {
280 usedTrack[bachelor] = kTRUE;
282 AliESDtrack *esdTrack = esd->GetTrack(bachelor);
285 esdTrack->GetPxPyPz(p);
291 esdTrack->GetCovarianceXYZPxPyPz(cov);
294 esdTrack->GetESDpid(pid);
296 vcascade->AddDaughter(
297 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
298 esdTrack->GetLabel(),
304 (Short_t)esdTrack->GetSign(),
305 esdTrack->GetITSClusterMap(),
308 AliAODTrack::kSecondary)
312 cerr << "Error: event " << iEvent << " cascade " << nCascade
313 << " track " << bachelor << " has already been used!" << endl;
316 // Add the primary track of the cascade (if any)
318 } // end of the loop on cascades
322 for (Int_t nV0 = 0; nV0 < nV0s; ++nV0) {
324 if (usedV0[nV0]) continue; // skip if aready added to the AOD
326 AliESDv0 *v0 = esd->GetV0(nV0);
329 v0->GetXYZ(posV0[0], posV0[1], posV0[2]);
331 v0->GetPosCov(covV0);
334 new(vertices[jVertices++]) AliAODVertex(posV0,
339 primary->AddDaughter(vV0);
341 Int_t posFromV0 = v0->GetPindex();
342 Int_t negFromV0 = v0->GetNindex();
344 // Add the positive tracks from the V0
346 if (!usedTrack[posFromV0]) {
348 usedTrack[posFromV0] = kTRUE;
350 AliESDtrack *esdTrack = esd->GetTrack(posFromV0);
353 esdTrack->GetPxPyPz(p);
359 esdTrack->GetCovarianceXYZPxPyPz(cov);
362 esdTrack->GetESDpid(pid);
365 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
366 esdTrack->GetLabel(),
371 (Short_t)esdTrack->GetSign(),
372 esdTrack->GetITSClusterMap(),
375 AliAODTrack::kSecondary)
379 cerr << "Error: event " << iEvent << " V0 " << nV0
380 << " track " << posFromV0 << " has already been used!" << endl;
383 // Add the negative tracks from the V0
385 if (!usedTrack[negFromV0]) {
387 usedTrack[negFromV0] = kTRUE;
389 AliESDtrack *esdTrack = esd->GetTrack(negFromV0);
392 esdTrack->GetPxPyPz(p);
398 esdTrack->GetCovarianceXYZPxPyPz(cov);
401 esdTrack->GetESDpid(pid);
404 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
405 esdTrack->GetLabel(),
411 (Short_t)esdTrack->GetSign(),
412 esdTrack->GetITSClusterMap(),
415 AliAODTrack::kSecondary)
419 cerr << "Error: event " << iEvent << " V0 " << nV0
420 << " track " << negFromV0 << " has already been used!" << endl;
423 } // end of the loop on V0s
425 // Kinks: it is a big mess the access to the information in the kinks
426 // The loop is on the tracks in order to find the mother and daugther of each kink
429 for (Int_t iTrack=0; iTrack<nTracks; ++iTrack) {
432 AliESDtrack * track = esd->GetTrack(iTrack);
435 Int_t ikink = track->GetKinkIndex(0);
438 // Negative kink index: mother, positive: daughter
440 // Search for the second track of the kink
442 for (Int_t jTrack = iTrack+1; jTrack<nTracks; ++jTrack) {
444 AliESDtrack * track1 = esd->GetTrack(jTrack);
446 Int_t jkink = track1->GetKinkIndex(0);
448 if ( TMath::Abs(ikink)==TMath::Abs(jkink) ) {
450 // The two tracks are from the same kink
452 if (usedKink[TMath::Abs(ikink)-1]) continue; // skip used kinks
455 Int_t idaughter = -1;
457 if (ikink<0 && jkink>0) {
462 else if (ikink>0 && jkink<0) {
468 cerr << "Error: Wrong combination of kink indexes: "
469 << ikink << " " << jkink << endl;
473 // Add the mother track
475 AliAODTrack * mother = NULL;
477 if (!usedTrack[imother]) {
479 usedTrack[imother] = kTRUE;
481 AliESDtrack *esdTrack = esd->GetTrack(imother);
484 esdTrack->GetPxPyPz(p);
490 esdTrack->GetCovarianceXYZPxPyPz(cov);
493 esdTrack->GetESDpid(pid);
497 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
498 esdTrack->GetLabel(),
504 (Short_t)esdTrack->GetSign(),
505 esdTrack->GetITSClusterMap(),
508 AliAODTrack::kPrimary);
509 primary->AddDaughter(mother);
512 cerr << "Error: event " << iEvent << " kink " << TMath::Abs(ikink)-1
513 << " track " << imother << " has already been used!" << endl;
516 // Add the kink vertex
517 AliESDkink * kink = esd->GetKink(TMath::Abs(ikink)-1);
519 AliAODVertex * vkink =
520 new(vertices[jVertices++]) AliAODVertex(kink->GetPosition(),
524 AliAODVertex::kKink);
525 // Add the daughter track
527 AliAODTrack * daughter = NULL;
529 if (!usedTrack[idaughter]) {
531 usedTrack[idaughter] = kTRUE;
533 AliESDtrack *esdTrack = esd->GetTrack(idaughter);
536 esdTrack->GetPxPyPz(p);
542 esdTrack->GetCovarianceXYZPxPyPz(cov);
545 esdTrack->GetESDpid(pid);
549 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
550 esdTrack->GetLabel(),
556 (Short_t)esdTrack->GetSign(),
557 esdTrack->GetITSClusterMap(),
560 AliAODTrack::kPrimary);
561 vkink->AddDaughter(daughter);
564 cerr << "Error: event " << iEvent << " kink " << TMath::Abs(ikink)-1
565 << " track " << idaughter << " has already been used!" << endl;
577 // Tracks (primary and orphan)
579 for (Int_t nTrack = 0; nTrack < nTracks; ++nTrack) {
582 if (usedTrack[nTrack]) continue;
584 AliESDtrack *esdTrack = esd->GetTrack(nTrack);
587 esdTrack->GetPxPyPz(p);
593 esdTrack->GetCovarianceXYZPxPyPz(cov);
596 esdTrack->GetESDpid(pid);
598 Float_t impactXY, impactZ;
600 esdTrack->GetImpactParameters(impactXY,impactZ);
603 // track inside the beam pipe
605 primary->AddDaughter(
606 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
607 esdTrack->GetLabel(),
613 (Short_t)esdTrack->GetSign(),
614 esdTrack->GetITSClusterMap(),
617 AliAODTrack::kPrimary)
621 // outside the beam pipe: orphan track
622 new(tracks[jTracks++]) AliAODTrack(esdTrack->GetID(),
623 esdTrack->GetLabel(),
629 (Short_t)esdTrack->GetSign(),
630 esdTrack->GetITSClusterMap(),
633 AliAODTrack::kOrphan);
635 } // end of loop on tracks
638 // Access to the AOD container of vertices
639 TClonesArray &clusters = *(aod->GetClusters());
643 Int_t nClusters = esd->GetNumberOfCaloClusters();
645 for (Int_t iClust=0; iClust<nClusters; ++iClust) {
647 AliESDCaloCluster * cluster = esd->GetCaloCluster(iClust);
649 Int_t id = cluster->GetID();
651 Float_t energy = cluster->GetClusterEnergy();
653 cluster->GetGlobalPosition(x);
654 Float_t * covMatrix = NULL;
655 Float_t * pid = NULL;
656 AliAODVertex *prodVertex = primary;
657 AliAODTrack *primTrack = NULL;
658 Char_t ttype=AliAODCluster::kUndef;
660 if (cluster->IsPHOS()) ttype=AliAODCluster::kPHOSNeutral;
661 else if (cluster->IsEMCAL()) {
663 if (cluster->GetClusterType() == AliESDCaloCluster::kPseudoCluster)
664 ttype = AliAODCluster::kEMCALPseudoCluster;
666 ttype = AliAODCluster::kEMCALClusterv1;
670 new(clusters[jClusters++]) AliAODCluster(id,
680 } // end of loop on clusters
687 // fill the tree for this event
689 } // end of event loop
691 aodTree->GetUserInfo()->Add(aod);
696 // write the tree to the specified file
697 outFile = aodTree->GetCurrentFile();