* provided "as is" without express or implied warranty. *
**************************************************************************/
-/*
-$Log$
-Revision 1.18 2002/02/20 16:14:41 hristov
-fParticleBuffer points to object which doesn't belong to AliStack, do not delete it (J.Chudoba)
-
-Revision 1.17 2001/12/05 08:51:56 hristov
-The default constructor now creates no objects (thanks to r.Brun). Some corrections required by the previous changes.
-
-Revision 1.16 2001/11/20 09:27:55 hristov
-Possibility to investigate a primary of not yet loaded particle (I.Hrivnacova)
-
-Revision 1.15 2001/09/04 15:10:37 hristov
-Additional protection is included to avoid some problems using Hijing
-
-Revision 1.14 2001/08/30 09:44:06 hristov
-VertexSource_t added to avoid the warnings
-
-Revision 1.13 2001/08/29 13:31:42 morsch
-Protection against (fTreeK == 0) in destructor.
-
-Revision 1.12 2001/07/27 13:03:13 hristov
-Default Branch split level set to 99
-
-Revision 1.11 2001/07/27 12:34:20 jchudoba
-remove the dummy argument in GetEvent method
-
-Revision 1.10 2001/07/20 10:13:54 morsch
-In Particle(Int_t) use GetEntriesFast to speed up the procedure.
-
-Revision 1.9 2001/07/03 08:10:57 hristov
-J.Chudoba's changes merged correctly with the HEAD
-
-Revision 1.6 2001/05/31 06:59:06 fca
-Clean setting and deleting of fParticleBuffer
-
-Revision 1.5 2001/05/30 12:18:46 hristov
-Loop variables declared once
-
-Revision 1.4 2001/05/25 07:25:20 hristov
-AliStack destructor corrected (I.Hrivnacova)
-
-Revision 1.3 2001/05/22 14:33:16 hristov
-Minor changes
-
-Revision 1.2 2001/05/17 05:49:39 fca
-Reset pointers to daughters
-
-Revision 1.1 2001/05/16 14:57:22 alibrary
-New files for folders and Stack
-
-*/
+/* $Id$ */
///////////////////////////////////////////////////////////////////////////////
// //
// //
///////////////////////////////////////////////////////////////////////////////
-#include <iostream.h>
+#include <Riostream.h>
#include <TObjArray.h>
#include <TParticle.h>
#include "AliRun.h"
#include "AliModule.h"
#include "AliHit.h"
-//#include "ETrackBits.h"
ClassImp(AliStack)
-//_____________________________________________________________________________
-AliStack::AliStack(Int_t size)
+//_______________________________________________________________________
+AliStack::AliStack():
+ fParticles(0),
+ fParticleMap(0),
+ fParticleFileMap(0),
+ fParticleBuffer(0),
+ fTreeK(0),
+ fNtrack(0),
+ fNprimary(0),
+ fCurrent(-1),
+ fCurrentPrimary(-1),
+ fHgwmk(0),
+ fLoadPoint(0)
{
//
- // Constructor
+ // Default constructor
//
-
- // Create the particles arrays
- fParticles = new TClonesArray("TParticle",1000);
- fParticleMap = new TObjArray(size);
- fParticleBuffer = 0;
- fNtrack = 0;
- fNprimary = 0;
- fCurrent = -1;
- fCurrentPrimary = -1;
- fTreeK = 0;
}
+//_______________________________________________________________________
+AliStack::AliStack(Int_t size):
+ fParticles(new TClonesArray("TParticle",1000)),
+ fParticleMap(new TObjArray(size)),
+ fParticleFileMap(0),
+ fParticleBuffer(0),
+ fTreeK(0),
+ fNtrack(0),
+ fNprimary(0),
+ fCurrent(-1),
+ fCurrentPrimary(-1),
+ fHgwmk(0),
+ fLoadPoint(0)
+{
+ //
+ // Constructor
+ //
+}
-//_____________________________________________________________________________
-AliStack::AliStack()
+//_______________________________________________________________________
+AliStack::AliStack(const AliStack& st):
+ TVirtualMCStack(st),
+ fParticles(0),
+ fParticleMap(0),
+ fParticleFileMap(0),
+ fParticleBuffer(0),
+ fTreeK(0),
+ fNtrack(0),
+ fNprimary(0),
+ fCurrent(-1),
+ fCurrentPrimary(-1),
+ fHgwmk(0),
+ fLoadPoint(0)
{
//
- // Default constructor
+ // Copy constructor
//
-
- // Create the particles arrays
- fParticles = 0;
- fParticleMap = 0;
- fParticleBuffer = 0;
- fNtrack = 0;
- fCurrent = -1;
- fNprimary = 0;
- fCurrentPrimary = -1;
- fTreeK = 0;
+ st.Copy(*this);
}
+//_______________________________________________________________________
+void AliStack::Copy(AliStack&) const
+{
+ Fatal("Copy","Not implemented!\n");
+}
-//_____________________________________________________________________________
+//_______________________________________________________________________
AliStack::~AliStack()
{
//
delete fParticles;
}
delete fParticleMap;
- if (fTreeK) delete fTreeK;
+ delete fTreeK;
}
//
//_____________________________________________________________________________
void AliStack::SetTrack(Int_t done, Int_t parent, Int_t pdg, Float_t *pmom,
Float_t *vpos, Float_t *polar, Float_t tof,
- AliMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
+ TMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
{
//
// Load a track on the stack
// ntr on output the number of the track stored
//
- Float_t mass;
- const Int_t kfirstdaughter=-1;
- const Int_t klastdaughter=-1;
// const Float_t tlife=0;
//
// also, this method is potentially dangerous if the mass
// used in the MC is not the same of the PDG database
//
- mass = TDatabasePDG::Instance()->GetParticle(pdg)->Mass();
+ Float_t mass = TDatabasePDG::Instance()->GetParticle(pdg)->Mass();
Float_t e=TMath::Sqrt(mass*mass+pmom[0]*pmom[0]+
pmom[1]*pmom[1]+pmom[2]*pmom[2]);
// printf("Loading mass %f ene %f No %d ip %d parent %d done %d pos %f %f %f mom %f %f %f kS %d m \n",
// mass,e,fNtrack,pdg,parent,done,vpos[0],vpos[1],vpos[2],pmom[0],pmom[1],pmom[2],kS);
- TClonesArray &particles = *fParticles;
- TParticle* particle
- = new(particles[fLoadPoint++])
- TParticle(pdg, is, parent, -1, kfirstdaughter, klastdaughter,
- pmom[0], pmom[1], pmom[2], e, vpos[0], vpos[1], vpos[2], tof);
- particle->SetPolarisation(TVector3(polar[0],polar[1],polar[2]));
- particle->SetWeight(weight);
- particle->SetUniqueID(mech);
- if(!done) particle->SetBit(kDoneBit);
-
-
- // Declare that the daughter information is valid
- particle->SetBit(kDaughtersBit);
- // Add the particle to the stack
- fParticleMap->AddAtAndExpand(particle, fNtrack);
- if(parent>=0) {
- particle = (TParticle*) fParticleMap->At(parent);
- if (particle) {
- particle->SetLastDaughter(fNtrack);
- if(particle->GetFirstDaughter()<0) particle->SetFirstDaughter(fNtrack);
- }
- else {
- printf("Error in AliStack::SetTrack: Parent %d does not exist\n",parent);
- }
- }
- else {
- //
- // This is a primary track. Set high water mark for this event
- fHgwmk = fNtrack;
- //
- // Set also number if primary tracks
- fNprimary = fHgwmk+1;
- fCurrentPrimary++;
- }
- ntr = fNtrack++;
+ SetTrack(done, parent, pdg, pmom[0], pmom[1], pmom[2], e,
+ vpos[0], vpos[1], vpos[2], tof, polar[0], polar[1], polar[2],
+ mech, ntr, weight, is);
}
//_____________________________________________________________________________
Double_t px, Double_t py, Double_t pz, Double_t e,
Double_t vx, Double_t vy, Double_t vz, Double_t tof,
Double_t polx, Double_t poly, Double_t polz,
- AliMCProcess mech, Int_t &ntr, Float_t weight, Int_t is)
+ TMCProcess mech, Int_t &ntr, Double_t weight, Int_t is)
{
//
// Load a track on the stack
fParticleMap->AddAtAndExpand(particle, fNtrack);//CHECK!!
if(parent>=0) {
- particle = (TParticle*) fParticleMap->At(parent);
+ particle = dynamic_cast<TParticle*>(fParticleMap->At(parent));
if (particle) {
particle->SetLastDaughter(fNtrack);
if(particle->GetFirstDaughter()<0) particle->SetFirstDaughter(fNtrack);
}
//_____________________________________________________________________________
-void AliStack::GetNextTrack(Int_t &mtrack, Int_t &ipart, Float_t *pmom,
- Float_t &e, Float_t *vpos, Float_t *polar,
- Float_t &tof)
+TParticle* AliStack::GetNextTrack(Int_t& itrack)
+{
+ //
+ // Returns next track from stack of particles
+ //
+
+
+ TParticle* track = GetNextParticle();
+
+ if (track) {
+ itrack = fCurrent;
+ track->SetBit(kDoneBit);
+ }
+ else
+ itrack = -1;
+
+ return track;
+}
+
+/*
+//_____________________________________________________________________________
+void AliStack::GetNextTrack(Int_t& itrack, Int_t& pdg,
+ Double_t& px, Double_t& py, Double_t& pz, Double_t& e,
+ Double_t& vx, Double_t& vy, Double_t& vz, Double_t& tof,
+ Double_t& polx, Double_t& poly, Double_t& polz)
{
//
// Return next track from stack of particles
TParticle* track = GetNextParticle();
// cout << "GetNextTrack():" << fCurrent << fNprimary << endl;
- if(track) {
- mtrack=fCurrent;
- ipart=track->GetPdgCode();
- pmom[0]=track->Px();
- pmom[1]=track->Py();
- pmom[2]=track->Pz();
- e =track->Energy();
- vpos[0]=track->Vx();
- vpos[1]=track->Vy();
- vpos[2]=track->Vz();
+ if (track) {
+ itrack = fCurrent;
+ pdg = track->GetPdgCode();
+ px = track->Px();
+ py = track->Py();
+ pz = track->Pz();
+ e = track->Energy();
+ vx = track->Vx();
+ vy = track->Vy();
+ vz = track->Vz();
+ tof = track->T();
TVector3 pol;
track->GetPolarisation(pol);
- polar[0]=pol.X();
- polar[1]=pol.Y();
- polar[2]=pol.Z();
- tof=track->T();
+ polx = pol.X();
+ poly = pol.Y();
+ polz = pol.Z();
track->SetBit(kDoneBit);
// cout << "Filled params" << endl;
}
else
- mtrack=-1;
+ itrack = -1;
//
// stop and start timer when we start a primary track
fTimer.Start();
}
+*/
+//_____________________________________________________________________________
+TParticle* AliStack::GetPrimaryForTracking(Int_t i)
+{
+ //
+ // Returns i-th primary particle if it is flagged to be tracked,
+ // 0 otherwise
+ //
+
+ TParticle* particle = Particle(i);
+
+ if (!particle->TestBit(kDoneBit))
+ return particle;
+ else
+ return 0;
+}
+
//_____________________________________________________________________________
void AliStack::PurifyKine()
if(i<=fHgwmk) map[i]=i ;
else {
map[i] = -99;
- if((part=(TParticle*) particles.At(i))) {
+ if((part=dynamic_cast<TParticle*>(particles.At(i)))) {
+//
+// Check of this track should be kept for physics reasons
+ if (KeepPhysics(part)) KeepTrack(i);
+//
part->ResetBit(kDaughtersBit);
part->SetFirstDaughter(-1);
part->SetLastDaughter(-1);
// Invalid daughter information for the parent of the first particle
// generated. This may or may not be the current primary according to
// whether decays have been recorded among the primaries
- part = (TParticle *)particles.At(fHgwmk+1);
+ part = dynamic_cast<TParticle*>(particles.At(fHgwmk+1));
particles.At(part->GetFirstMother())->ResetBit(kDaughtersBit);
// Second pass, build map between old and new numbering
for(i=fHgwmk+1; i<fNtrack; i++) {
map[i]=nkeep;
// If old and new are different, have to move the pointer
if(i!=nkeep) particles[nkeep]=particles.At(i);
- part = (TParticle*) particles.At(nkeep);
+ part = dynamic_cast<TParticle*>(particles.At(nkeep));
// as the parent is always *before*, it must be already
// in place. This is what we are checking anyway!
// Fix daughters information
for (i=fHgwmk+1; i<nkeep; i++) {
- part = (TParticle *)particles.At(i);
+ part = dynamic_cast<TParticle*>(particles.At(i));
parent = part->GetFirstMother();
if(parent>=0) {
- father = (TParticle *)particles.At(parent);
+ father = dynamic_cast<TParticle*>(particles.At(parent));
if(father->TestBit(kDaughtersBit)) {
if(i<father->GetFirstDaughter()) father->SetFirstDaughter(i);
TList* hitLists = gAlice->GetHitLists();
TIter next(hitLists);
TCollection *hitList;
- while((hitList = (TCollection*)next())) {
+ while((hitList = dynamic_cast<TCollection*>(next()))) {
TIter nexthit(hitList);
AliHit *hit;
- while((hit = (AliHit*)nexthit())) {
+ while((hit = dynamic_cast<AliHit*>(nexthit()))) {
hit->SetTrack(map[hit->GetTrack()]);
}
}
TObjArray* modules = gAlice->Modules();
TIter nextmod(modules);
AliModule *detector;
- while((detector = (AliModule*)nextmod())) {
+ while((detector = dynamic_cast<AliModule*>(nextmod()))) {
detector->RemapTrackHitIDs(map.GetArray());
+ detector->RemapTrackReferencesIDs(map.GetArray());
}
// Now the output bit, from fHgwmk to nkeep we write everything and we erase
if(nkeep>fParticleFileMap.GetSize()) fParticleFileMap.Set(Int_t (nkeep*1.5));
for (i=fHgwmk+1; i<nkeep; ++i) {
- fParticleBuffer = (TParticle*) particles.At(i);
- fParticleFileMap[i]=(Int_t) fTreeK->GetEntries();
+ fParticleBuffer = dynamic_cast<TParticle*>(particles.At(i));
+ fParticleFileMap[i]=static_cast<Int_t>(fTreeK->GetEntries());
fTreeK->Fill();
particles[i]=fParticleBuffer=0;
}
// delete [] map;
}
+Bool_t AliStack::KeepPhysics(TParticle* part)
+{
+ //
+ // Some particles have to kept on the stack for reasons motivated
+ // by physics analysis. Decision is put here.
+ //
+ Bool_t keep = kFALSE;
+ //
+ // Keep first-generation daughter from primaries with heavy flavor
+ //
+ Int_t parent = part->GetFirstMother();
+ if (parent >= 0 && parent <= fHgwmk) {
+ TParticle* father = dynamic_cast<TParticle*>(Particles()->At(parent));
+ Int_t kf = father->GetPdgCode();
+ kf = TMath::Abs(kf);
+ Int_t kfl = kf;
+ // meson ?
+ if (kfl > 10) kfl/=100;
+ // baryon
+ if (kfl > 10) kfl/=10;
+ if (kfl > 10) kfl/=10;
+ if (kfl >= 4) {
+ keep = kTRUE;
+ }
+ }
+ return keep;
+}
+
//_____________________________________________________________________________
void AliStack::FinishEvent()
{
TObject *part;
for(Int_t i=0; i<fHgwmk+1; ++i)
if((part=fParticleMap->At(i))) {
- fParticleBuffer = (TParticle*) part;
- fParticleFileMap[i]= (Int_t) fTreeK->GetEntries();
+ fParticleBuffer = dynamic_cast<TParticle*>(part);
+ fParticleFileMap[i]= static_cast<Int_t>(fTreeK->GetEntries());
fTreeK->Fill();
//PH (*fParticleMap)[i]=fParticleBuffer=0;
fParticleBuffer=0;
Int_t curr=track;
while(1) {
- particle=(TParticle*)fParticleMap->At(curr);
+ particle=dynamic_cast<TParticle*>(fParticleMap->At(curr));
// If the particle is flagged the three from here upward is saved already
if(particle->TestBit(kKeepBit)) return;
}
//_____________________________________________________________________________
-void AliStack::SetHighWaterMark(Int_t nt)
+void AliStack::SetHighWaterMark(Int_t)
{
//
// Set high water mark for last track in event
Int_t nentries = fParticles->GetEntriesFast();
// algorithmic way of getting entry index
// (primary particles are filled after secondaries)
- Int_t entry;
- if (i<fNprimary)
- entry = i+fNtrack-fNprimary;
- else
- entry = i-fNprimary;
+ Int_t entry = TreeKEntry(i);
// check whether algorithmic way and
// and the fParticleFileMap[i] give the same;
// give the fatal error if not
new ((*fParticles)[nentries]) TParticle(*fParticleBuffer);
fParticleMap->AddAt((*fParticles)[nentries],i);
}
- //PH return (TParticle *) (*fParticleMap)[i];
- return (TParticle *) fParticleMap->At(i);
+ //PH return dynamic_cast<TParticle *>((*fParticleMap)[i]);
+ return dynamic_cast<TParticle*>(fParticleMap->At(i));
+}
+
+//_____________________________________________________________________________
+TParticle* AliStack::ParticleFromTreeK(Int_t id) const
+{
+//
+// return pointer to TParticle with label id
+//
+ Int_t entry;
+ if ((entry = TreeKEntry(id)) < 0) return 0;
+ if (fTreeK->GetEntry(entry)<=0) return 0;
+ return fParticleBuffer;
+}
+
+//_____________________________________________________________________________
+Int_t AliStack::TreeKEntry(Int_t id) const
+{
+//
+// return entry number in the TreeK for particle with label id
+// return negative number if label>fNtrack
+//
+ Int_t entry;
+ if (id<fNprimary)
+ entry = id+fNtrack-fNprimary;
+ else
+ entry = id-fNprimary;
+ return entry;
}
//_____________________________________________________________________________
// Dumps particle i in the stack
//
- //PH ((TParticle*) (*fParticleMap)[i])->Print();
- ((TParticle*) fParticleMap->At(i))->Print();
+ //PH dynamic_cast<TParticle*>((*fParticleMap)[i])->Print();
+ dynamic_cast<TParticle*>(fParticleMap->At(i))->Print();
}
//_____________________________________________________________________________
"\n\n=======================================================================\n");
for (Int_t i=0;i<fNtrack;i++)
{
- TParticle* particle = (TParticle*) particles[i];
+ TParticle* particle = dynamic_cast<TParticle*>(particles[i]);
if (particle) {
printf("-> %d ",i); particle->Print();
printf("--------------------------------------------------------------\n");
TParticle *part;
int i;
for(i=0; i<fHgwmk+1; i++) {
- part = (TParticle *)particles.At(i);
+ part = dynamic_cast<TParticle*>(particles.At(i));
if(part) if(!part->TestBit(kDaughtersBit)) {
part->SetFirstDaughter(-1);
part->SetLastDaughter(-1);
// search secondaries
//for(Int_t i=fNtrack-1; i>=0; i--) {
for(Int_t i=fNtrack-1; i>fHgwmk; i--) {
- particle = (TParticle*) fParticleMap->At(i);
+ particle = dynamic_cast<TParticle*>(fParticleMap->At(i));
if ((particle) && (!particle->TestBit(kDoneBit))) {
fCurrent=i;
//cout << "GetNextParticle() - secondary "
// take next primary if all secondaries were done
while (fCurrentPrimary>=0) {
fCurrent = fCurrentPrimary;
- particle = (TParticle*) fParticleMap->At(fCurrentPrimary--);
+ particle = dynamic_cast<TParticle*>(fParticleMap->At(fCurrentPrimary--));
if ((particle) && (!particle->TestBit(kDoneBit))) {
//cout << "GetNextParticle() - primary "
// << fNtrack << " " << fHgwmk << " " << fCurrent << endl;
}
//__________________________________________________________________________________________
-void AliStack::MakeTree(Int_t event, const char *file)
+void AliStack::MakeTree(Int_t event, const char * /*file*/)
{
//
// Make Kine tree and creates branch for writing particles
TBranch *branch=0;
// Make Kinematics Tree
char hname[30];
-// printf("\n MakeTree called %d", event);
if (!fTreeK) {
sprintf(hname,"TreeK%d",event);
fTreeK = new TTree(hname,"Kinematics");
}
}
-//_____________________________________________________________________________
Bool_t AliStack::GetEvent(Int_t event)
{
//
// Get Kine Tree from file
char treeName[20];
sprintf(treeName,"TreeK%d",event);
- fTreeK = (TTree*)gDirectory->Get(treeName);
+ fTreeK = dynamic_cast<TTree*>(gDirectory->Get(treeName));
if (fTreeK)
fTreeK->SetBranchAddress("Particles", &fParticleBuffer);
else {
- Error("GetEvent","cannot find Kine Tree for event:%d\n",event);
+ // Error("GetEvent","cannot find Kine Tree for event:%d\n",event);
+ Warning("GetEvent","cannot find Kine Tree for event:%d\n",event);
return kFALSE;
}
// printf("\n primaries %d", fNprimary);
// printf("\n tracks %d", fNtrack);
- Int_t size = (Int_t)fTreeK->GetEntries();
+ Int_t size = static_cast<Int_t>(fTreeK->GetEntries());
ResetArrays(size);
return kTRUE;
}
-
-//----------------------------------------------------------------------