StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
StarKinematics.cxx
1 #include "StarKinematics.h"
2 #include "StarGenerator/EVENT/StarGenEvent.h"
3 #include "StarGenerator/EVENT/StarGenParticle.h"
4 #include "StarGenerator/UTIL/StarParticleData.h"
5 #include "StarGenerator/UTIL/StarRandom.h"
6 
7 #include <vector>
8 #include <string>
9 #include <algorithm>
10 #include <random>
11 
12 #define random myrandom
13 
14 // Tokenizes a string similar to boost::split() from boost/algorithm/string.hpp
15 // For motivation see https://github.com/star-bnl/star-sw/issues/81
16 namespace {
17 vector<string> split(const string &s, const string &sep_chars)
18 {
19  string::size_type prev_pos = 0, pos = 0;
20  vector<string> result;
21 
22  while ((pos = s.find_first_of(sep_chars, pos)) != string::npos) {
23  result.push_back(s.substr(prev_pos, pos - prev_pos));
24  pos += 1;
25  prev_pos = pos;
26  }
27  result.push_back(s.substr(prev_pos));
28 
29  return result;
30 }
31 }
32 
33 // ----------------------------------------------------------------------------
34 
37 
38 static std::random_device _stl_rd;
39 static std::mt19937 _mt19937( _stl_rd() );
40 
41 StarGenEvent *gEvent = 0;
42 StarGenEvent *gUser = 0;
43 
44 // ----------------------------------------------------------------------------
45 StarKinematics::StarKinematics( const Char_t *name ) : StarGenerator(name)
46 {
47  mEvent = new StarGenEvent("kine"); gEvent = mEvent;
48  mUser = new StarGenEvent("user"); gUser = mUser;
49 }
50 // ----------------------------------------------------------------------------
52 {
53  return kStOK;
54 }
55 // ----------------------------------------------------------------------------
57 {
58 
59  // Copy user event into mEvent
60  for ( Int_t i=0;i<mUser->GetNumberOfParticles(); i++ )
61  {
62  mEvent -> AddParticle( (*mUser)[i] );
63  }
64 
65  // And clear the user event
66  mUser->Clear();
67 
68  return kStOK;
69 }
70 // ----------------------------------------------------------------------------
72 {
73  return kStOK;
74 }
75 // ----------------------------------------------------------------------------
77 {
78  StarGenParticle *p = mUser->AddParticle();
80  return p;
81 }
82 // ----------------------------------------------------------------------------
84 {
85  TParticlePDG *pdg = data(type); assert(pdg);
86  Int_t id = pdg->PdgCode();
89  p->SetMass( pdg->Mass() );
90  p->SetId( id );
91  return p;
92 }
93 // ----------------------------------------------------------------------------
94 void StarKinematics::Kine(Int_t ntrack, const Char_t *_type, Double_t ptlow, Double_t pthigh,
95  Double_t ylow, Double_t yhigh,
96  Double_t philow, Double_t phihigh )
97 {
98 
99  std::string type = _type;
100  std::vector<std::string> types = split(_type, ", ");
101 
102  for ( Int_t i=0;i<ntrack;i++ )
103  {
104 
105  std::shuffle( types.begin(), types.end(), _mt19937 );
106  type = types[0];
107 
108  StarGenParticle *p = AddParticle(type.c_str());
109 
110  // Sample pt, eta, phi
111  if ( 0 == IAttr("energy") ) { // uniform in pT
112  double pt = random(ptlow, pthigh);
113  double y = random(ylow, yhigh );
114  double phi= random(philow, phihigh );
115  double m = p->GetMass();
116 
117  double mt = pt;
118  if ( IAttr("rapidity" ) ) {
119  // switch from pseudorapidity to plain vanilla rapidity
120  mt = TMath::Sqrt( pt*pt + m*m );
121  }
122 
123  double px = pt * TMath::Cos( phi );
124  double py = pt * TMath::Sin( phi );
125  double pz = mt * TMath::SinH( y );
126  double E = mt * TMath::CosH( y );
127 
128  p->SetPx( px );
129  p->SetPy( py );
130  p->SetPz( pz );
131  p->SetEnergy( E );
132 
133  p->SetVx( 0. ); // put vertex at 0,0,0,0
134  p->SetVy( 0. );
135  p->SetVz( 0. );
136  p->SetTof( 0. );
137  }
138  if ( IAttr("energy") ) { // uniform in energy.
139 
140  assert( 0==IAttr("rapidity") ); // only flat in eta, not rapidity
141 
142  double E = random(ptlow, pthigh);
143  double y = random(ylow, yhigh ); // y is eta here, not rapidity
144  double phi= random(philow, phihigh );
145  double m = p->GetMass();
146  double pmom = TMath::Sqrt(E*E - m*m);
147  double pt = 2.0 * pmom * TMath::Exp( -y ) / ( 1 + TMath::Exp( -2.0*y ) );
148 
149  double mt = pt;
150  if ( IAttr("rapidity" ) ) {
151  // switch from pseudorapidity to plain vanilla rapidity
152  mt = TMath::Sqrt( pt*pt + m*m );
153  }
154 
155  double px = pt * TMath::Cos( phi );
156  double py = pt * TMath::Sin( phi );
157  double pz = mt * TMath::SinH( y );
158  //double E = mt * TMath::CosH( y );
159 
160  p->SetPx( px );
161  p->SetPy( py );
162  p->SetPz( pz );
163  p->SetEnergy( E );
164 
165  p->SetVx( 1e-11); // put vertex at 0,0,0,0
166  p->SetVy( 1e-11);
167  p->SetVz( 1e-11);
168  p->SetTof( 0. );
169  }
170 
171 
172  }
173 
174 }
175 // ----------------------------------------------------------------------------
176 void StarKinematics::Dist( Int_t ntrack, const Char_t *_type, TF1 *ptFunc, TF1 *etaFunc, TF1 *phiFunc )
177 {
178 
179  std::string type = _type;
180  std::vector<std::string> types = split(_type, ", ");
181 
182  for ( Int_t i=0; i<ntrack; i++ )
183  {
184 
185  std::shuffle( types.begin(), types.end(), _mt19937 );
186  type = types[0];
187 
188  StarGenParticle *p = AddParticle(type.c_str());
189 
190  Double_t pt = ptFunc -> GetRandom();
191  Double_t y = etaFunc -> GetRandom();
192  Double_t phi = (phiFunc) ? phiFunc->GetRandom() : random( 0., TMath::TwoPi() );
193  Double_t m = p->GetMass();
194 
195  double mt = pt;
196  if ( IAttr("rapidity" ) ) {
197  // switch from pseudorapidity to plain vanilla rapidity
198  mt = TMath::Sqrt( pt*pt + m*m );
199  }
200 
201  double px = pt * TMath::Cos( phi );
202  double py = pt * TMath::Sin( phi );
203  double pz = mt * TMath::SinH( y );
204  double E = mt * TMath::CosH( y );
205 
206  p->SetPx( px );
207  p->SetPy( py );
208  p->SetPz( pz );
209  p->SetEnergy( E );
210 
211  p->SetVx( 0. ); // put vertex at 0,0,0,0
212  p->SetVy( 0. );
213  p->SetVz( 0. );
214  p->SetTof( 0. );
215 
216  }
217 }
218 // ----------------------------------------------------------------------------
219 void StarKinematics::Dist( Int_t ntrack, const Char_t *_type, TH1 *ptFunc, TH1 *etaFunc, TH1 *phiFunc )
220 {
221  std::string type = _type;
222  std::vector<std::string> types = split(_type, ", ");
223 
224  for ( Int_t i=0; i<ntrack; i++ )
225  {
226 
227  std::shuffle( types.begin(), types.end(), _mt19937 );
228  type = types[0];
229 
230  StarGenParticle *p = AddParticle(type.c_str());
231 
232  Double_t pt = ptFunc -> GetRandom();
233  Double_t y = etaFunc -> GetRandom();
234  Double_t phi = (phiFunc) ? phiFunc->GetRandom() : random( 0., TMath::TwoPi() );
235  Double_t m = p->GetMass();
236 
237  double mt = pt;
238  if ( IAttr("rapidity" ) ) {
239  // switch from pseudorapidity to plain vanilla rapidity
240  mt = TMath::Sqrt( pt*pt + m*m );
241  }
242 
243  double px = pt * TMath::Cos( phi );
244  double py = pt * TMath::Sin( phi );
245  double pz = mt * TMath::SinH( y );
246  double E = mt * TMath::CosH( y );
247 
248  p->SetPx( px );
249  p->SetPy( py );
250  p->SetPz( pz );
251  p->SetEnergy( E );
252 
253  p->SetVx( 0. ); // put vertex at 0,0,0,0
254  p->SetVy( 0. );
255  p->SetVz( 0. );
256  p->SetTof( 0. );
257 
258  }
259 }
260 // ----------------------------------------------------------------------------
261 const double deg2rad = TMath::DegToRad();
262 
263 void StarKinematics::Cosmic( int ntrack, const char* _type, double plow, double phigh, double radius, double zmin, double zmax, double dphi )
264 {
265  std::string type = _type;
266  std::vector<std::string> types = split(_type, ", ");
267 
268  for ( Int_t i=0; i<ntrack; i++ )
269  {
270 
271  std::shuffle( types.begin(), types.end(), _mt19937 );
272  type = types[0];
273 
274  StarGenParticle *p = AddParticle(type.c_str());
275 
276  // Generate a random vertex
277  double zvertex = random( zmin, zmax );
278  double phi = random( 0.0, TMath::TwoPi() );
279  double xvertex = radius * TMath::Cos(phi);
280  double yvertex = radius * TMath::Sin(phi);
281 
282  xvertex *= 10; // cm --> mm per HEPEVT standard
283  yvertex *= 10; // cm --> mm
284  zvertex *= 10; // cm --> mm
285 
286  // Initialize vertex X,Y ... to get unit vector pointing to beam line
287  TVector3 vertex(xvertex,yvertex,0);
288 
289  // Unit vector pointing away from beamline
290  TVector3 direct = vertex.Unit();
291 
292  // Sample momentum distribution
293  double pmag = random(plow, phigh);
294 
295  // Momentum vector pointing in towards the beamline
296  _momentum = -pmag * direct;
297 
298  // Now, randomize phi and theta by +/- dphi degrees about the momentum axis
299  phi = _momentum.Phi() + deg2rad * random( -dphi, +dphi );
300  double theta = _momentum.Theta() + deg2rad * random( -dphi, +dphi );
301 
302  _momentum.SetPhi(phi);
303  _momentum.SetTheta(theta);
304 
305  Double_t m = p->GetMass();
306 
307  Double_t E2 = _momentum.Mag2() + m*m;
308  Double_t E = sqrt(E2);
309 
310  p->SetPx( _momentum.Px() );
311  p->SetPy( _momentum.Py() );
312  p->SetPz( _momentum.Pz() );
313  p->SetEnergy( E );
314 
315  p->SetVx( xvertex );
316  p->SetVy( yvertex );
317  p->SetVz( zvertex );
318  p->SetTof( 0. );
319 
320  }
321 }
322 // ----------------------------------------------------------------------------
StarGenParticle * AddParticle()
Int_t PreGenerate()
Developers may provide a pre-generate method which will execute before Generate().
void SetPx(Float_t px)
Set the x-component of the momentum.
static StarRandom & Instance()
Obtain the single instance of the random number generator.
Definition: StarRandom.cxx:87
Int_t GetNumberOfParticles()
Obtain the number of particles in the event record.
Definition: StarGenEvent.h:187
void SetVy(Float_t vy)
Set the y-component of the start vertex.
Yet another particle class.
Int_t PostGenerate()
Developers may provide a post-generate method which will execute after Generate().
ABC for defining event generator interfaces.
Definition: StarGenerator.h:34
StarGenEvent * mEvent
Generated event.
void SetVz(Float_t vz)
Set the z-component of the start vertex.
void SetVx(Float_t vx)
Set the x-component of the start vertex.
virtual void Clear(const Option_t *opts="part,data")
Clear the event.
static StarParticleData & instance()
Returns a reference to the single instance of this class.
void SetId(Int_t id)
Interface to PDG information.
void SetStatus(Int_t status)
Set the status code of the particle according to the HEPEVT standard.
void Dist(Int_t ntrack, const Char_t *type, TF1 *pt, TF1 *y, TF1 *phi=0)
void SetPz(Float_t pz)
Set the z-component of the momentum.
A class for providing random number generation.
Definition: StarRandom.h:30
void SetMass(Float_t mass)
Set the mass.
Int_t Generate()
Generate event.
void SetTof(Float_t tof)
Set the tof.
Base class for event records.
Definition: StarGenEvent.h:81
void Cosmic(int ntrack, const char *type="mu+", double plow=3.0, double phigh=10.0, double radius=300.0, double zmin=-3.0, double zmax=+3.0, double dtheta=15.0)
Definition: Stypes.h:40
void SetPy(Float_t py)
Set the y-component of the momentum.
void SetEnergy(Float_t energy)
Set the energy.
Float_t GetMass()
Get the mass.
void Kine(Int_t ntrack, const Char_t *type="pi+,pi-,K+,K-,proton,antiproton", Double_t ptlow=0.0, Double_t pthigh=500.0, Double_t ylow=-10.0, Double_t yhigh=+10.0, Double_t philow=0.0, Double_t phihigh=TMath::TwoPi())
StarGenParticle * AddParticle()