]> git.uio.no Git - u/mrichter/AliRoot.git/blame - PWG/muon/AliAODMuonReplicator.cxx
Coverity fixes (Diego)
[u/mrichter/AliRoot.git] / PWG / muon / AliAODMuonReplicator.cxx
CommitLineData
26ba01d4 1/**************************************************************************
2* Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3* *
4* Author: The ALICE Off-line Project. *
5* Contributors are mentioned in the code where appropriate. *
6* *
7* Permission to use, copy, modify and distribute this software and its *
8* documentation strictly for non-commercial purposes is hereby granted *
9* without fee, provided that the above copyright notice appears in all *
10* copies and that both the copyright notice and this permission notice *
11* appear in the supporting documentation. The authors make no claims *
12* about the suitability of this software for any purpose. It is *
13* provided "as is" without express or implied warranty. *
14**************************************************************************/
15
16// $Id$
17
3d270be0 18//
19// Implementation of a branch replicator
20// to produce slim muon and dimuon aods.
21//
22// This replicator is in charge of replicating the tracks,vertices and dimuons
23// branches of the standard AOD into muon AODs (AliAOD.Muons.root and
24// AliAOD.Dimuons.root)
25//
26// The tracks are filtered so that only muon tracks (and only muon tracks
27// that pass the trackCut if present) make it to the output aods
28//
29// The vertices are filtered so that only the primary vertices make it
30// to the output aods.
31//
32// The dimuons are recreated here, according to the set of tracks
33// that pass the trackCut (that set may be the same as the input set,
34// but to be 100% safe, we always recreate the dimuons).
35//
36// Author: L. Aphecetche (Subatech)
37
26ba01d4 38#include "AliAODMuonReplicator.h"
39#include "AliAnalysisCuts.h"
40#include "AliAODEvent.h"
41#include "AliAODTrack.h"
3d270be0 42#include "AliAODDimuon.h"
14d6fad5 43#include "AliAODMCHeader.h"
44#include "AliAODMCParticle.h"
26ba01d4 45#include <cassert>
46
47ClassImp(AliAODMuonReplicator)
48
49//_____________________________________________________________________________
50AliAODMuonReplicator::AliAODMuonReplicator(const char* name, const char* title,
14d6fad5 51 AliAnalysisCuts* trackCut,
52 AliAnalysisCuts* vertexCut,
53 Int_t mcMode)
54:AliAODBranchReplicator(name,title),
26ba01d4 55fTrackCut(trackCut), fTracks(0x0),
3d270be0 56fVertexCut(vertexCut), fVertices(0x0),
57fDimuons(0x0),
5393f2c0 58fVZERO(0x0),
14d6fad5 59fList(0x0),
60fMCParticles(0x0),
61fMCHeader(0x0),
62fMCMode(mcMode),
63fLabelMap(),
64fParticleSelected()
26ba01d4 65{
66 // default ctor
67}
68
69//_____________________________________________________________________________
70AliAODMuonReplicator::~AliAODMuonReplicator()
71{
72 // dtor
73 delete fTrackCut;
74 delete fVertexCut;
75 delete fList;
76}
77
14d6fad5 78//_____________________________________________________________________________
79void AliAODMuonReplicator::SelectParticle(Int_t i)
80{
81 // taking the absolute values here, need to take care
82 // of negative daughter and mother
83 // IDs when setting!
84
85 if (!IsParticleSelected(TMath::Abs(i)))
86 {
87 fParticleSelected.Add(TMath::Abs(i),1);
88 }
89}
90
91//_____________________________________________________________________________
92Bool_t AliAODMuonReplicator::IsParticleSelected(Int_t i)
93{
94 // taking the absolute values here, need to take
95 // care with negative daughter and mother
96 // IDs when setting!
97 return (fParticleSelected.GetValue(TMath::Abs(i))==1);
98}
99
100
101//_____________________________________________________________________________
102void AliAODMuonReplicator::CreateLabelMap(const AliAODEvent& source)
103{
104 //
105 // this should be called once all selections are done
106 //
107
108 fLabelMap.Delete();
109
110 TClonesArray* mcParticles = static_cast<TClonesArray*>(source.FindListObject(AliAODMCParticle::StdBranchName()));
111
112 Int_t i(0);
113 Int_t j(0);
114
115 TIter next(mcParticles);
116
117 while ( next() )
118 {
119 if (IsParticleSelected(i))
120 {
121 fLabelMap.Add(i,j++);
122 }
123 ++i;
124 }
125}
126
127//_____________________________________________________________________________
128Int_t AliAODMuonReplicator::GetNewLabel(Int_t i)
129{
130 // Gets the label from the new created Map
131 // Call CreatLabelMap before
132 // otherwise only 0 returned
133 return fLabelMap.GetValue(TMath::Abs(i));
134}
135
136//_____________________________________________________________________________
137void AliAODMuonReplicator::FilterMC(const AliAODEvent& source)
138{
139 // Filter MC information
140
141 fMCHeader->Reset();
142 fMCParticles->Clear("C");
143
144 AliAODMCHeader* mcHeader(0x0);
145 TClonesArray* mcParticles(0x0);
146
147 fParticleSelected.Delete();
148
eb7548df 149 if ( fMCMode>=2 && !fTracks->GetEntries() ) return;
150 // for fMCMode==1 we only copy MC information for events where there's at least one muon track
14d6fad5 151
152 mcHeader = static_cast<AliAODMCHeader*>(source.FindListObject(AliAODMCHeader::StdBranchName()));
153
154 if ( mcHeader )
155 {
156 *fMCHeader = *mcHeader;
157 }
158
159 mcParticles = static_cast<TClonesArray*>(source.FindListObject(AliAODMCParticle::StdBranchName()));
160
161 if ( mcParticles && fMCMode>=2 )
162 {
163 // loop on (kept) muon tracks to find their ancestors
164 TIter nextMT(fTracks);
165 AliAODTrack* mt;
14d6fad5 166
167 while ( ( mt = static_cast<AliAODTrack*>(nextMT()) ) )
168 {
169 Int_t label = mt->GetLabel();
170
171 while ( label >= 0 )
172 {
173 SelectParticle(label);
174 AliAODMCParticle* mother = static_cast<AliAODMCParticle*>(mcParticles->UncheckedAt(label));
175 if (!mother)
176 {
177 AliError("Got a null mother ! Check that !");
178 label = -1;
179 }
180 else
181 {
182 label = mother->GetMother();
183 }
184 }
185 }
186
187 CreateLabelMap(source);
188
189 // Actual filtering and label remapping (shamelessly taken for the implementation of AliAODHandler::StoreMCParticles)
190 TIter nextMC(mcParticles);
191 AliAODMCParticle* p;
192 Int_t nmc(0);
193 Int_t nmcout(0);
194
195 while ( ( p = static_cast<AliAODMCParticle*>(nextMC()) ) )
196 {
197 AliAODMCParticle c(*p);
198
199 if ( IsParticleSelected(nmc) )
200 {
201 //
202 Int_t d0 = p->GetDaughter(0);
203 Int_t d1 = p->GetDaughter(1);
204 Int_t m = p->GetMother();
205
206 // other than for the track labels, negative values mean
207 // no daughter/mother so preserve it
208
209 if(d0<0 && d1<0)
210 {
211 // no first daughter -> no second daughter
212 // nothing to be done
213 // second condition not needed just for sanity check at the end
214 c.SetDaughter(0,d0);
215 c.SetDaughter(1,d1);
216 } else if(d1 < 0 && d0 >= 0)
217 {
218 // Only one daughter
219 // second condition not needed just for sanity check at the end
220 if(IsParticleSelected(d0))
221 {
222 c.SetDaughter(0,GetNewLabel(d0));
223 } else
224 {
225 c.SetDaughter(0,-1);
226 }
227 c.SetDaughter(1,d1);
228 }
229 else if (d0 > 0 && d1 > 0 )
230 {
231 // we have two or more daughters loop on the stack to see if they are
232 // selected
233 Int_t d0tmp = -1;
234 Int_t d1tmp = -1;
235 for (int id = d0; id<=d1;++id)
236 {
237 if (IsParticleSelected(id))
238 {
239 if(d0tmp==-1)
240 {
241 // first time
242 d0tmp = GetNewLabel(id);
243 d1tmp = d0tmp; // this is to have the same schema as on the stack i.e. with one daugther d0 and d1 are the same
244 }
245 else d1tmp = GetNewLabel(id);
246 }
247 }
248 c.SetDaughter(0,d0tmp);
249 c.SetDaughter(1,d1tmp);
250 } else
251 {
252 AliError(Form("Unxpected indices %d %d",d0,d1));
253 }
254
255 if ( m < 0 )
256 {
257 c.SetMother(m);
258 } else
259 {
260 if (IsParticleSelected(m))
261 {
262 c.SetMother(GetNewLabel(m));
263 }
264 else
265 {
266 AliError(Form("PROBLEM Mother not selected %d", m));
267 }
268 }
269
270 new ((*fMCParticles)[nmcout++]) AliAODMCParticle(c);
271 }
272
273 ++nmc;
274 }
275
276 // now remap the tracks...
277
278 TIter nextTrack(fTracks);
279 AliAODTrack* t;
280
281 while ( ( t = static_cast<AliAODTrack*>(nextTrack()) ) )
282 {
283 t->SetLabel(GetNewLabel(t->GetLabel()));
284 }
285
286 }
287 else if ( mcParticles )
288 {
289 // simple copy of input MC particles to ouput MC particles
290 TIter nextMC(mcParticles);
291 AliAODMCParticle* p;
292 Int_t nmcout(0);
293
294 while ( ( p = static_cast<AliAODMCParticle*>(nextMC()) ) )
295 {
296 new ((*fMCParticles)[nmcout++]) AliAODMCParticle(*p);
297 }
298 }
299
300 AliDebug(1,Form("input mc %d output mc %d",
301 mcParticles ? mcParticles->GetEntries() : 0,
302 fMCParticles ? fMCParticles->GetEntries() : 0));
303
304}
305
26ba01d4 306//_____________________________________________________________________________
307TList* AliAODMuonReplicator::GetList() const
308{
309 // return (and build if not already done) our internal list of managed objects
310 if (!fList)
311 {
3d270be0 312 fTracks = new TClonesArray("AliAODTrack",30);
26ba01d4 313 fTracks->SetName("tracks");
3d270be0 314
315 fVertices = new TClonesArray("AliAODVertex",2);
26ba01d4 316 fVertices->SetName("vertices");
14d6fad5 317
3d270be0 318 fDimuons = new TClonesArray("AliAODDimuon",2);
319 fDimuons->SetName("dimuons");
320
5393f2c0 321 fVZERO = new AliAODVZERO;
322
3d270be0 323 fList = new TList;
324 fList->SetOwner(kTRUE);
325
26ba01d4 326 fList->Add(fTracks);
327 fList->Add(fVertices);
3d270be0 328 fList->Add(fDimuons);
5393f2c0 329 fList->Add(fVZERO);
eb7548df 330
14d6fad5 331 if ( fMCMode > 0 )
332 {
333 fMCHeader = new AliAODMCHeader;
334 fMCParticles = new TClonesArray("AliAODMCParticle",1000);
335 fMCParticles->SetName(AliAODMCParticle::StdBranchName());
336 fList->Add(fMCHeader);
337 fList->Add(fMCParticles);
338 }
26ba01d4 339 }
340 return fList;
341}
342
343//_____________________________________________________________________________
344void AliAODMuonReplicator::ReplicateAndFilter(const AliAODEvent& source)
345{
346 // Replicate (and filter if filters are there) the relevant parts we're interested in AODEvent
347
26ba01d4 348 assert(fTracks!=0x0);
eb7548df 349
5393f2c0 350 *fVZERO = *(source.GetVZEROData());
351
26ba01d4 352 fTracks->Clear("C");
353 TIter next(source.GetTracks());
354 AliAODTrack* t;
355 Int_t ntracks(0);
14d6fad5 356 Int_t input(0);
26ba01d4 357
358 while ( ( t = static_cast<AliAODTrack*>(next()) ) )
359 {
14d6fad5 360 if ( t->IsMuonTrack() )
361 {
362 ++input;
363 }
364
26ba01d4 365 if ( !fTrackCut || fTrackCut->IsSelected(t) )
366 {
367 new((*fTracks)[ntracks++]) AliAODTrack(*t);
368 }
369 }
370
371 assert(fVertices!=0x0);
372 fVertices->Clear("C");
373 TIter nextV(source.GetVertices());
374 AliAODVertex* v;
375 Int_t nvertices(0);
376
377 while ( ( v = static_cast<AliAODVertex*>(nextV()) ) )
378 {
379 if ( !fVertexCut || fVertexCut->IsSelected(v) )
380 {
381 AliAODVertex* tmp = v->CloneWithoutRefs();
eb7548df 382 AliAODVertex* copiedVertex = new((*fVertices)[nvertices++]) AliAODVertex(*tmp);
383 // to insure the main vertex retains the ncontributors information
384 // (which is otherwise computed dynamically from
385 // references to tracks, which we do not keep in muon aods...)
386 // we set it here
387 copiedVertex->SetNContributors(v->GetNContributors());
26ba01d4 388 delete tmp;
389 }
390 }
391
3d270be0 392 fDimuons->Clear("C");
393
394 // as there might be a track cut (different from the one of the main filtering),
395 // we must recreate the dimuon completely from scratch to be 100% safe...
396
397 Int_t ndimuons(0);
398
399 for ( Int_t i = 0; i < ntracks; ++i )
400 {
401 for ( Int_t j = i+1; j < ntracks; ++j )
402 {
403 new((*fDimuons)[ndimuons++]) AliAODDimuon(fTracks->At(i),fTracks->At(j));
404 }
405 }
14d6fad5 406
407 AliDebug(1,Form("input mu tracks=%d tracks=%d vertices=%d ndimuons=%d",
408 input,fTracks->GetEntries(),fVertices->GetEntries(),fDimuons->GetEntries()));
409
410 // Finally, deal with MC information, if needed
411
412 if ( fMCMode > 0 )
413 {
414 FilterMC(source);
415 }
26ba01d4 416}
417