1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
19 // Container class for AliGenerator and AfterBurners
20 // (which are AliGenerators as well) through recursion.
21 // The container is itself an AliGenerator a
22 // what is stored are not the pointers to the generators directly
23 // but to objects of type
24 // AliGenCocktailAfterBurner entry.
25 // The class provides also iterator functionality.
26 // Author: andreas.morsch@cern.ch and piotr.skowronski@cern.ch
28 // 24.09.2001 Piotr Skowronski
30 // fNEvents replaced with AliRunLoader::GetNumberOfEvents()
34 #include <Riostream.h>
37 #include <TObjArray.h>
38 #include <TParticle.h>
40 #include "AliGenCocktailAfterBurner.h"
41 #include "AliGenCocktailEntry.h"
42 #include "AliGenCocktailEventHeader.h"
43 #include "AliCollisionGeometry.h"
48 ClassImp(AliGenCocktailAfterBurner)
49 /*********************************************************************/
50 /*********************************************************************/
52 AliGenCocktailAfterBurner::AliGenCocktailAfterBurner():
54 fAfterBurnerEntries(new TList()),
55 fGenerationDone(kFALSE),
57 fCollisionGeometries(0),
67 cout<<"AliGenCocktailAfterBurner::AliGenCocktailAfterBurner()"<<endl;
68 SetName("AliGenCocktailAfterBurner");
69 SetTitle("AliGenCocktailAfterBurner");
72 /*********************************************************************/
74 AliGenCocktailAfterBurner::~AliGenCocktailAfterBurner()
78 if (fInternalStacks) //delete stacks
80 fInternalStacks->SetOwner();
81 delete fInternalStacks;
83 if (fAfterBurnerEntries) delete fAfterBurnerEntries; //delete entries
84 Int_t numberOfEvents = AliRunLoader::Instance()->GetNumberOfEventsPerRun();
85 if (fCollisionGeometries) {
86 for (Int_t i = 0; i < (numberOfEvents + fNBgEvents); i++)
87 if (fCollisionGeometries[i]) delete fCollisionGeometries[i];
88 delete[] fCollisionGeometries;
91 for (Int_t i = 0; i < (numberOfEvents + fNBgEvents); i++)
92 if (fHeaders[i]) delete fHeaders[i];
96 /*********************************************************************/
97 /*********************************************************************/
99 void AliGenCocktailAfterBurner::
100 AddAfterBurner(AliGenerator *AfterBurner, char* Name, Float_t RateExp)
103 // Forward parameters to the new AfterBurner
105 if (gDebug>0)cout<<"AliGenCocktailAfterBurner::AddAfterBurner Named "<<Name<<endl;
107 if(TestBit(kPtRange))
108 AfterBurner->SetPtRange(fPtMin,fPtMax);
109 if(TestBit(kMomentumRange))
110 AfterBurner->SetMomentumRange(fPMin,fPMax);
112 AfterBurner->SetYRange(fYMin,fYMax);
113 AfterBurner->SetPhiRange(fPhiMin*180/TMath::Pi(),fPhiMax*180/TMath::Pi());
114 AfterBurner->SetThetaRange(fThetaMin*180/TMath::Pi(),fThetaMax*180/TMath::Pi());
115 AfterBurner->SetOrigin(fOrigin[0], fOrigin[1], fOrigin[2]);
116 AfterBurner->SetSigma(fOsigma[0], fOsigma[1], fOsigma[2]);
117 AfterBurner->SetVertexSmear(fVertexSmear);
118 AfterBurner->SetTrackingFlag(fTrackIt);
119 AfterBurner->SetVertexSource(kContainer);
121 // Add AfterBurner to list
123 AliGenCocktailEntry *entry =
124 new AliGenCocktailEntry(AfterBurner, Name, RateExp);
125 fAfterBurnerEntries->Add(entry);
130 /*********************************************************************/
131 /*********************************************************************/
133 void AliGenCocktailAfterBurner::Init()
136 Int_t numberOfEvents = AliRunLoader::Instance()->GetNumberOfEventsPerRun();
137 fGenerationDone = kFALSE;
138 if (fInternalStacks) //delete stacks
140 fInternalStacks->SetOwner();
141 fInternalStacks->Delete(); //clean after previous generation cycle
144 if (fCollisionGeometries) {
145 for (Int_t i = 0; i < (numberOfEvents + fNBgEvents); i++)
146 if (fCollisionGeometries[i]) delete fCollisionGeometries[i];
147 delete[] fCollisionGeometries;
150 for (Int_t i = 0; i < (numberOfEvents + fNBgEvents); i++)
151 if (fHeaders[i]) delete fHeaders[i];
155 this->AliGenCocktail::Init();
157 if (gDebug>0) cout<<"AliGenCocktailAfterBurner::Init"<<endl;
158 TIter next(fAfterBurnerEntries);
159 AliGenCocktailEntry *entry;
161 // Loop over generators and initialize
162 while((entry = (AliGenCocktailEntry*)next())) {
163 entry->Generator()->Init();
166 /*********************************************************************/
167 /*********************************************************************/
169 void AliGenCocktailAfterBurner::Generate()
173 // Firsts runs each generator for all events
174 // than after burners ones for each event
176 // It generates and processes all events during
178 // In next calls it just returns already generated
179 // and processed events to the gAlice
182 cout<<"#####################################"<<endl
183 <<"#AliGenCocktailAfterBurner::Generate#"<<endl
184 <<"#####################################"<<endl;
191 {//if generation is done (in first call)
192 //just copy particles from the stack to the gAlice
193 SetTracks(++fCurrentEvent);
194 fHeader = fHeaders[fCurrentEvent];
195 gAlice->SetGenEventHeader(fHeader);
196 cout<<"Returning event " << fCurrentEvent<<endl;
200 { //Here we are in the first call of the method
201 Int_t numberOfEvents = AliRunLoader::Instance()->GetNumberOfEventsPerRun();
202 cout << "Number of events per run" << numberOfEvents << endl;
204 eventVertex.Set(3 * (numberOfEvents + fNBgEvents));
207 fInternalStacks = new TObjArray(numberOfEvents + fNBgEvents); //Create array of internal stacks
208 fCollisionGeometries = new AliCollisionGeometry*[numberOfEvents + fNBgEvents]; //Create array of collision geometries
209 fHeaders = new AliGenCocktailEventHeader*[numberOfEvents + fNBgEvents]; //Create array of headers
211 for(i = 0; i < numberOfEvents + fNBgEvents; i++)
213 stack = new AliStack(10000);
215 fInternalStacks->Add(stack);
217 for (Int_t j = 0; j < 3; j++) eventVertex[3 * i + j] = fVertex[j];
218 fHeaders[i] = new AliGenCocktailEventHeader();
220 /*********************************************************************/
221 TIter next(fEntries);
222 AliGenCocktailEntry *entry;
223 AliGenCocktailEntry *e1;
224 AliGenCocktailEntry *e2;
225 const TObjArray *partArray;
227 // Loop over generators and generate events
229 while((entry = (AliGenCocktailEntry*)next()))
232 cout<<"Generator "<<igen<<" : "<<entry->GetName()<<endl;
233 /***********************************************/
234 //First generator for all evenets, than second for all events, etc...
235 for(i = 0; i < numberOfEvents + fNBgEvents; i++)
237 cout<<" EVENT "<<i << endl;
239 partArray = stack->Particles();
240 fCurrentGenerator = entry->Generator();
241 fCurrentGenerator->SetStack(stack);
248 entry->SetFirst((partArray->GetEntriesFast())+1);
250 // Set the vertex for the generator
252 fCurrentGenerator->SetVertex(eventVertex.At(ioff), eventVertex.At(ioff + 1), eventVertex.At(ioff + 2));
253 fHeader = fHeaders[i];
254 // Set the vertex for the cocktail
256 for (Int_t j=0; j<3; j++) v[j] = eventVertex.At(ioff + j);
257 fHeader->SetPrimaryVertex(v);
259 fCurrentGenerator->Generate();
261 entry->SetLast(partArray->GetEntriesFast());
263 if (fCurrentGenerator->ProvidesCollisionGeometry())
264 fCollisionGeometries[i] =
265 new AliCollisionGeometry(*(fCurrentGenerator->CollisionGeometry()));
267 /***********************************************/
270 while((entry = (AliGenCocktailEntry*)next()))
274 for ( entry=FirstGenerator();entry;entry=NextGenerator() )
278 for (FirstGeneratorPair(e1,e2); (e1&&e2); NextGeneratorPair(e1,e2) )
280 printf("\n -----------------------------");
286 /***********************************************/
287 /*******After Burners Processing****************/
288 /***********************************************/
289 TIter nextAfterBurner(fAfterBurnerEntries);
290 AliGenCocktailEntry *afterBurnerEntry;
291 Int_t iab =0; //number of current after burner / counter
293 cout<<"\n\nRunning After Burners"<<endl;
294 while((afterBurnerEntry = (AliGenCocktailEntry*)nextAfterBurner()))
296 cout<<"After Burner "<<iab++<<" :"<<afterBurnerEntry->GetName()<<endl;
297 fCurrentGenerator = afterBurnerEntry->Generator();
298 fCurrentGenerator->Generate();
300 cout<<endl<<"Finished. Processed "<<iab<<" After Burners"<<endl;
302 /***********************************************/
303 /***********************************************/
304 /***********************************************/
306 fGenerationDone=kTRUE;
307 SetTracks(0); //copy event 0 to gAlice stack
309 /*********************************************************************/
310 // Pass the header to gAlice
311 fHeader = fHeaders[0];
312 gAlice->SetGenEventHeader(fHeader);
315 /*********************************************************************/
316 /*********************************************************************/
318 AliStack* AliGenCocktailAfterBurner::GetStack(Int_t n) const
320 //Returns the pointer to the N'th stack (event)
321 if( ( n<0 ) || ( n >= (GetNumberOfEvents()) ) )
323 Fatal("AliGenCocktailAfterBurner::GetStack","Asked for non existing stack (%d)",n);
326 return ((AliStack*) fInternalStacks->At(n) );
329 /*********************************************************************/
330 /*********************************************************************/
332 AliCollisionGeometry* AliGenCocktailAfterBurner::GetCollisionGeometry(Int_t n) const
334 //Returns the pointer to the N'th stack (event)
335 if( ( n<0 ) || ( n>=GetNumberOfEvents() ) )
337 Fatal("AliGenCocktailAfterBurner::GetCollisionGeometry","Asked for non existing stack (%d)",n);
340 return fCollisionGeometries[n];
343 /*********************************************************************/
344 /*********************************************************************/
346 void AliGenCocktailAfterBurner::SetActiveEventNumber(Int_t actev)
348 //Set Active Events Number and Active Stack
349 //There is only one active event number
350 //Made fo convinience of work with AfterBurners (HBT processor)
352 fActiveEvent = actev;
353 fActiveStack = GetStack(actev);
355 /*********************************************************************/
356 /*********************************************************************/
358 void AliGenCocktailAfterBurner::SetTracks(Int_t stackno)
360 //Method which copies tracks from given stack to the
362 AliStack* instack = GetStack(stackno);
366 Double_t px, py, pz, e, vx, vy, vz, tof, polx, poly, polz;
373 Int_t n = instack->GetNtrack();
376 cout<<"AliGenCocktailAfterBurner::SetTracks("<<stackno<<"). Number of particles is: "<<n<<"\n";
379 for(Int_t i = 0; i < n; i++)
382 p = instack->Particle(i);
383 done = !p->TestBit(kDoneBit);
384 parent = p->GetMother(0);
385 pdg = p->GetPdgCode();
394 p->GetPolarisation(pol);
398 mech = AliGenCocktailAfterBurner::IntToMCProcess(p->GetUniqueID());
399 weight = p->GetWeight();
401 gAlice->GetMCApp()->PushTrack(done, parent, pdg, px, py, pz, e, vx, vy, vz, tof,polx, poly, polz, mech, ntr, weight);
403 SetHighWaterMark(ntr) ;
407 /*********************************************************************/
408 /*********************************************************************/
410 TMCProcess AliGenCocktailAfterBurner::IntToMCProcess(Int_t no)
412 //Mothod used to convert uniqueID (integer) to TMCProcess type
413 const TMCProcess kMCprocesses[kMaxMCProcess] =
415 kPNoProcess, kPMultipleScattering, kPEnergyLoss, kPMagneticFieldL,
416 kPDecay, kPPair, kPCompton, kPPhotoelectric, kPBrem, kPDeltaRay,
417 kPAnnihilation, kPHadronic, kPNoProcess, kPEvaporation, kPNuclearFission,
418 kPNuclearAbsorption, kPPbarAnnihilation, kPNCapture, kPHElastic,
419 kPHInhelastic, kPMuonNuclear, kPTOFlimit,kPPhotoFission, kPNoProcess,
420 kPRayleigh, kPNoProcess, kPNoProcess, kPNoProcess, kPNull, kPStop
423 for (Int_t i = 0;i<kMaxMCProcess;i++)
425 if (kMCprocesses[i] == no)
427 return kMCprocesses[i];