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 **************************************************************************/
18 Revision 1.5 2000/06/09 20:35:32 morsch
19 All coding rule violations except RS3 corrected
21 Revision 1.4 2000/03/20 18:03:24 morsch
22 Change muon particle code to PDG code.
24 Revision 1.3 1999/09/29 09:24:08 fca
25 Introduction of the Copyright and cvs Log
33 #include "AliDimuCombinator.h"
36 #include <TClonesArray.h>
39 ClassImp(AliDimuCombinator)
40 AliDimuCombinator::AliDimuCombinator(TClonesArray* Partarray)
44 fNParticle=fPartArray->GetEntriesFast();
61 AliDimuCombinator::AliDimuCombinator(const AliDimuCombinator & combinator)
70 TParticle* AliDimuCombinator::FirstMuon()
72 // Single muon iterator: initialisation
74 fmuon1 = (TParticle*) fPartArray->UncheckedAt(fimuon1);
75 while(Type(fmuon1)!=kMuonPlus && Type(fmuon1)!=kMuonMinus) {
77 if (fimuon1 >= fimax1) {fmuon1=0; break;}
78 fmuon1 = (TParticle*) fPartArray->UncheckedAt(fimuon1);
83 TParticle* AliDimuCombinator::FirstMuonSelected()
85 // Single selected muon iterator: initialisation
86 TParticle * muon=FirstMuon();
87 while(muon!=0 && !Selected(muon)) {muon=NextMuon();}
92 TParticle* AliDimuCombinator::NextMuon()
94 // Single muon iterator: increment
96 if (fimuon1>=fNParticle) {fmuon1 = 0; return fmuon1;}
98 fmuon1 = (TParticle*) fPartArray->UncheckedAt(fimuon1);
99 while(Type(fmuon1)!=kMuonPlus && Type(fmuon1)!=kMuonMinus) {
101 if (fimuon1>=fimax1) {fmuon1 = 0; break;}
102 fmuon1 = (TParticle*) fPartArray->UncheckedAt(fimuon1);
107 TParticle* AliDimuCombinator::NextMuonSelected()
109 // Single selected muon iterator: increment
110 TParticle * muon=NextMuon();
111 while(muon !=0 && !Selected(muon)) {muon=NextMuon();}
116 void AliDimuCombinator::FirstPartner()
118 // Helper for dimuon iterator: initialisation
119 if (fimin1==fimin2) {
124 if (fimuon2 >= fimax2) {fmuon2=0; return;}
125 fmuon2 = (TParticle*) fPartArray->UncheckedAt(fimuon2);
126 while(Type(fmuon2)!=kMuonPlus && Type(fmuon2)!=kMuonMinus) {
128 if (fimuon2 >= fimax2) {fmuon2=0; break;}
129 fmuon2 = (TParticle*) fPartArray->UncheckedAt(fimuon2);
133 void AliDimuCombinator::FirstPartnerSelected()
135 // Helper for selected dimuon iterator: initialisation
137 while(fmuon2 !=0 && !Selected(fmuon2)) {NextPartner();}
141 void AliDimuCombinator::NextPartner()
143 // Helper for dimuon iterator: increment
145 if (fimuon2>=fimax2) {fmuon2 = 0; return;}
148 fmuon2 = (TParticle*) fPartArray->UncheckedAt(fimuon2);
150 while(Type(fmuon2)!=kMuonPlus && Type(fmuon2)!=kMuonMinus) {
152 if (fimuon2>=fimax2) {fmuon2 = 0; break;}
153 fmuon2 = (TParticle*) fPartArray->UncheckedAt(fimuon2);
157 void AliDimuCombinator::NextPartnerSelected()
159 // Helper for selected dimuon iterator: increment
161 while(fmuon2 !=0 && !Selected(fmuon2)) {NextPartner();}
165 TParticle* AliDimuCombinator::Partner()
167 // Returns current partner for muon to form a dimuon
171 void AliDimuCombinator::FirstMuonPair(TParticle* & muon1, TParticle* & muon2)
173 // Dimuon iterator: initialisation
180 void AliDimuCombinator::NextMuonPair(TParticle* & muon1, TParticle* & muon2)
182 // Dimuon iterator: increment
191 void AliDimuCombinator::FirstMuonPairSelected(TParticle* & muon1,
194 // Selected dimuon iterator: initialisation
196 FirstPartnerSelected();
201 void AliDimuCombinator::NextMuonPairSelected(TParticle* & muon1,
204 // Selected dimuon iterator: increment
205 NextPartnerSelected();
208 FirstPartnerSelected();
214 void AliDimuCombinator::ResetRange()
216 // Reset index ranges for single muons
218 fimax1=fimax2=fNParticle;
221 void AliDimuCombinator::SetFirstRange(Int_t from, Int_t to)
223 // Reset index range for first muon
226 if (fimax1 > fNParticle) fimax1=fNParticle;
229 void AliDimuCombinator::SetSecondRange(Int_t from, Int_t to)
231 // Reset index range for second muon
234 if (fimax2 > fNParticle) fimax2=fNParticle;
240 Bool_t AliDimuCombinator::Selected(TParticle* part)
242 // Selection cut for single muon
244 if (part==0) {return 0;}
246 if (part->Pt() > fPtMin && part->Eta()>fEtaMin && part->Eta()<fEtaMax) {
253 Bool_t AliDimuCombinator::Selected(TParticle* part1, TParticle* part2)
255 // Selection cut for dimuons
257 return Selected(part1)*Selected(part2);
262 Float_t AliDimuCombinator::Mass(TParticle* part1, TParticle* part2)
267 px=part1->Px()+part2->Px();
268 py=part1->Py()+part2->Py();
269 pz=part1->Pz()+part2->Pz();
270 e =part1->Energy()+part2->Energy();
271 Float_t p=px*px+py*py+pz*pz;
275 return TMath::Sqrt(e*e-p);
279 Float_t AliDimuCombinator::PT(TParticle* part1, TParticle* part2)
281 // Transverse momentum of dimuons
284 px=part1->Px()+part2->Px();
285 py=part1->Py()+part2->Py();
286 return TMath::Sqrt(px*px+py*py);
289 Float_t AliDimuCombinator::Pz(TParticle* part1, TParticle* part2)
291 // Pz of dimuon system
293 return part1->Pz()+part2->Pz();
296 Float_t AliDimuCombinator::Y(TParticle* part1, TParticle* part2)
298 // Rapidity of dimuon system
301 pz=part1->Pz()+part2->Pz();
302 e =part1->Energy()+part2->Energy();
303 return 0.5*TMath::Log((e+pz)/(e-pz));
307 void AliDimuCombinator::SmearGauss(Float_t width, Float_t & value)
309 // Apply gaussian smearing
311 value+=gRandom->Gaus(0, width);
316 Float_t AliDimuCombinator::DecayProbability(TParticle* part)
318 // Calculate decay probability for muons from pion and kaon decays
320 Float_t d, h, theta, cTau;
321 TParticle* parent = Parent(part);
322 Int_t ipar=Type(parent);
323 if (ipar==kPiPlus || ipar==kPiMinus) {
325 } else if (ipar==kKPlus || ipar==kKMinus) {
332 Float_t gammaBeta=(parent->P())/(parent->GetMass());
334 // this part is still very ALICE muon-arm specific
336 theta=parent->Theta();
337 h=90*TMath::Tan(theta);
340 d=4/TMath::Sin(theta);
342 d=90/TMath::Cos(theta);
346 return 1-TMath::Exp(-d/cTau/gammaBeta);
352 Float_t AliDimuCombinator::Weight(TParticle* part1, TParticle* part2)
356 Float_t wgt=(part1->GetWeight())*(part2->GetWeight());
358 if (Correlated(part1, part2)) {
359 return wgt/(Parent(part1)->GetWeight())*fRate1;
361 return wgt*fRate1*fRate2;
366 Float_t AliDimuCombinator::Weight(TParticle* part)
368 // Single muon weight
369 return (part->GetWeight())*(Parent(part)->GetWeight())*fRate1;
372 Bool_t AliDimuCombinator::Correlated(TParticle* part1, TParticle* part2)
374 // Check if muons are correlated
376 if (Origin(part1) == Origin(part2)) {
383 TParticle* AliDimuCombinator::Parent(TParticle* part)
385 // Return pointer to parent
387 return (TParticle*) (fPartArray->UncheckedAt(part->GetFirstMother()));
390 Int_t AliDimuCombinator::Origin(TParticle* part)
392 // Return pointer to primary particle
394 Int_t iparent= part->GetFirstMother();
395 if (iparent < 0) return iparent;
398 ip=((TParticle*) fPartArray->UncheckedAt(iparent))->GetFirstMother();
408 AliDimuCombinator& AliDimuCombinator::operator=(const AliDimuCombinator& rhs)
410 // Assignment operator