CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
EMShower.cc
Go to the documentation of this file.
1 //FAMOS Headers
6 
9 
10 #include <cmath>
11 
12 //#include "FastSimulation/Utilities/interface/Histos.h"
13 
14 using std::vector;
15 
16 
19  EMECALShowerParametrization* const myParam,
20  vector<const RawParticle*>* const myPart,
21  EcalHitMaker * const myGrid,
22  PreshowerHitMaker * const myPresh)
23 
24  : theParam(myParam),
25  thePart(myPart),
26  theGrid(myGrid),
27  thePreshower(myPresh),
28  random(engine),
29  myGammaGenerator(gamma)
30 {
31 
32  // Get the Famos Histos pointer
33  // myHistos = Histos::instance();
34  // myGammaGenerator = GammaFunctionGenerator::instance();
35  stepsCalculated=false;
36  hasPreshower = myPresh!=NULL;
37  theECAL = myParam->ecalProperties();
38  theHCAL = myParam->hcalProperties();
39  theLayer1 = myParam->layer1Properties();
40  theLayer2 = myParam->layer2Properties();
41 
42 
43  double fotos = theECAL->photoStatistics()
45 
46  nPart = thePart->size();
47  totalEnergy = 0.;
48  globalMaximum = 0.;
49  double meanDepth=0.;
50  // Initialize the shower parameters for each particle
51  for ( unsigned int i=0; i<nPart; ++i ) {
52  // std::cout << " AAA " << *(*thePart)[i] << std::endl;
53  // The particle and the shower energy
54  Etot.push_back(0.);
55  E.push_back(((*thePart)[i])->e());
56  totalEnergy+=E[i];
57  double lny = std::log ( E[i] / theECAL->criticalEnergy() );
58 
59  // Average and Sigma for T and alpha
60  double theMeanT = myParam->meanT(lny);
61  double theMeanAlpha = myParam->meanAlpha(lny);
62  double theMeanLnT = myParam->meanLnT(lny);
63  double theMeanLnAlpha = myParam->meanLnAlpha(lny);
64  double theSigmaLnT = myParam->sigmaLnT(lny);
65  double theSigmaLnAlpha = myParam->sigmaLnAlpha(lny);
66 
67  // The correlation matrix
68  double theCorrelation = myParam->correlationAlphaT(lny);
69  double rhop = std::sqrt( (1.+theCorrelation)/2. );
70  double rhom = std::sqrt( (1.-theCorrelation)/2. );
71 
72  // The number of spots in ECAL / HCAL
73  theNumberOfSpots.push_back(myParam->nSpots(E[i]));
74  // theNumberOfSpots.push_back(myParam->nSpots(E[i])*spotFraction);
75  //theNumberOfSpots = random->poissonShoot(myParam->nSpots(myPart->e()));
76 
77  // Photo-statistics
78  photos.push_back(E[i] * fotos);
79 
80  // The longitudinal shower development parameters
81  // Fluctuations of alpha, T and beta
82  double z1=0.;
83  double z2=0.;
84  double aa=0.;
85 
86  // Protect against too large fluctuations (a < 1) for small energies
87  while ( aa <= 1. ) {
88  z1 = random->gaussShoot(0.,1.);
89  z2 = random->gaussShoot(0.,1.);
90  aa = std::exp(theMeanLnAlpha + theSigmaLnAlpha * (z1*rhop-z2*rhom));
91  }
92 
93  a.push_back(aa);
94  T.push_back(std::exp(theMeanLnT + theSigmaLnT * (z1*rhop+z2*rhom)));
95  b.push_back((a[i]-1.)/T[i]);
96  maximumOfShower.push_back((a[i]-1.)/b[i]);
98  meanDepth += a[i]/b[i]*E[i];
99  // std::cout << " Adding max " << maximumOfShower[i] << " " << E[i] << " " <<maximumOfShower[i]*E[i] << std::endl;
100  // std::cout << std::setw(8) << std::setprecision(5) << " a /b " << a[i] << " " << b[i] << std::endl;
101  Ti.push_back(
102  a[i]/b[i] * (std::exp(theMeanLnAlpha)-1.) / std::exp(theMeanLnAlpha));
103 
104  // The parameters for the number of energy spots
105  TSpot.push_back(theParam->meanTSpot(theMeanT));
106  aSpot.push_back(theParam->meanAlphaSpot(theMeanAlpha));
107  bSpot.push_back((aSpot[i]-1.)/TSpot[i]);
108  // myHistos->fill("h7000",a[i]);
109  // myHistos->fill("h7002",E[i],a[i]);
110  }
111 // std::cout << " PS1 : " << myGrid->ps1TotalX0()
112 // << " PS2 : " << myGrid->ps2TotalX0()
113 // << " ECAL : " << myGrid->ecalTotalX0()
114 // << " HCAL : " << myGrid->hcalTotalX0()
115 // << " Offset : " << myGrid->x0DepthOffset()
116 // << std::endl;
117 
119  meanDepth/=totalEnergy;
120  // std::cout << " Total Energy " << totalEnergy << " Global max " << globalMaximum << std::endl;
121 }
122 
124 {
125  // TimeMe theT("EMShower::compute");
126 
127  // Determine the longitudinal intervals
128  // std::cout << " EMShower compute" << std::endl;
129  double dt;
130  double radlen;
131  int stps;
132  int first_Ecal_step=0;
133  int last_Ecal_step=0;
134 
135  // The maximum is in principe 8 (with 5X0 steps in the ECAL)
136  steps.reserve(20);
137 
138 // std::cout << " PS1 : " << theGrid->ps1TotalX0()
139 // << " PS2 : " << theGrid->ps2TotalX0()
140 // << " ECAL : " << theGrid->ecalTotalX0()
141 // << " HCAL : " << theGrid->hcalTotalX0()
142 // << " Offset : " << theGrid->x0DepthOffset()
143 // << std::endl;
144 
145 
146  radlen = -theGrid->x0DepthOffset();
147 
148  // Preshower Layer 1
149  radlen += theGrid->ps1TotalX0();
150  if ( radlen > 0. ) {
151  steps.push_back(Step(0,radlen));
152  radlen = 0.;
153  }
154 
155  // Preshower Layer 2
156  radlen += theGrid->ps2TotalX0();
157  if ( radlen > 0. ) {
158  steps.push_back(Step(1,radlen));
159  radlen = 0.;
160  }
161 
162  // add a step between preshower and ee
163  radlen += theGrid->ps2eeTotalX0();
164  if ( radlen > 0.) {
165  steps.push_back(Step(5,radlen));
166  radlen = 0.;
167  }
168 
169  // ECAL
170  radlen += theGrid->ecalTotalX0();
171  if ( radlen > 0. ) {
172  stps=(int)((radlen+2.5)/5.);
173  // stps=(int)((radlen+.5)/1.);
174  if ( stps == 0 ) stps = 1;
175  dt = radlen/(double)stps;
176  Step step(2,dt);
177  first_Ecal_step=steps.size();
178  for ( int ist=0; ist<stps; ++ist )
179  steps.push_back(step);
180  last_Ecal_step=steps.size()-1;
181  radlen = 0.;
182  }
183 
184  // I should had a gap here !
185 
186  // HCAL
187  radlen += theGrid->hcalTotalX0();
188  if ( radlen > 0. ) {
189  double dtFrontHcal=theGrid->totalX0()-theGrid->hcalTotalX0();
190  // One single step for the full HCAL
191  if(dtFrontHcal<30.)
192  {
193  dt=30.-dtFrontHcal;
194  Step step(3,dt);
195  steps.push_back(step);
196  }
197  }
198 
199  nSteps=steps.size();
200  if(nSteps==0) return;
201  double ESliceTot=0.;
202  double MeanDepth=0.;
203  depositedEnergy.resize(nSteps);
204  meanDepth.resize(nSteps);
205  double t=0.;
206 
207  int offset=0;
208  for(unsigned iStep=0;iStep<nSteps;++iStep)
209  {
210  ESliceTot=0.;
211  MeanDepth=0.;
212  double realTotalEnergy=0;
213  dt=steps[iStep].second;
214  t+=dt;
215  for ( unsigned int i=0; i<nPart; ++i ) {
216  depositedEnergy[iStep].push_back(deposit(t,a[i],b[i],dt));
217  ESliceTot +=depositedEnergy[iStep][i];
218  MeanDepth += deposit(t,a[i]+1.,b[i],dt)/b[i]*a[i];
219  realTotalEnergy+=depositedEnergy[iStep][i]*E[i];
220  }
221 
222  if( ESliceTot > 0. ) // can happen for the shower tails; this depth will be skipped anyway
223  MeanDepth/=ESliceTot;
224  else
225  MeanDepth=t-dt;
226 
227  meanDepth[iStep]=MeanDepth;
228  if(realTotalEnergy<0.001)
229  {
230  offset-=1;
231  }
232  }
233 
234  innerDepth=meanDepth[first_Ecal_step];
235  if(last_Ecal_step+offset>=0)
236  outerDepth=meanDepth[last_Ecal_step+offset];
237  else
239 
240  stepsCalculated=true;
241 }
242 
243 void
245 
246  double t = 0.;
247  double dt = 0.;
249 
250  // Prepare the grids in EcalHitMaker
251  // theGrid->setInnerAndOuterDepth(innerDepth,outerDepth);
252  float pstot=0.;
253  float ps2tot=0.;
254  float ps1tot=0.;
255  bool status=false;
256  // double E1 = 0.; // Energy layer 1
257  // double E2 = 0.; // Energy layer 2
258  // double n1 = 0.; // #mips layer 1
259  // double n2 = 0.; // #mips layer 2
260  // double E9 = 0.; // Energy ECAL
261 
262  // Loop over all segments for the longitudinal development
263  for (unsigned iStep=0; iStep<nSteps; ++iStep ) {
264 
265  // The length of the shower in this segment
266  dt = steps[iStep].second;
267 
268  // std::cout << " Detector " << steps[iStep].first << " t " << t << " " << dt << std::endl;
269 
270  // The elapsed length
271  t += dt;
272 
273  // In what detector are we ?
274  unsigned detector=steps[iStep].first;
275 
276  bool presh1 = detector==0;
277  bool presh2 = detector==1;
278  bool ecal = detector==2;
279  bool hcal = detector==3;
280  bool vfcal = detector==4;
281  bool gap = detector==5;
282 
283  // Temporary. Will be removed
284  if ( theHCAL==NULL) hcal=false;
285 
286  // Keep only ECAL for now
287  if ( vfcal ) continue;
288 
289  // Nothing to do in the gap
290  if( gap ) continue;
291 
292  // cout << " t = " << t << endl;
293  // Build the grid of crystals at this ECAL depth
294  // Actually, it might be useful to check if this grid is empty or not.
295  // If it is empty (because no crystal at this depth), it is of no use
296  // (and time consuming) to generate the spots
297 
298 
299  // middle of the step
300  double tt = t-0.5*dt;
301 
302  double realTotalEnergy=0.;
303  for ( unsigned int i=0; i<nPart; ++i ) {
304  realTotalEnergy += depositedEnergy[iStep][i]*E[i];
305  }
306 
307 // std::cout << " Step " << tt << std::endl;
308 // std::cout << "ecal " << ecal << " hcal " << hcal <<std::endl;
309 
310  // If the amount of energy is greater than 1 MeV, make a new grid
311  // otherwise put in the previous one.
312  bool usePreviousGrid=(realTotalEnergy<0.001);
313 
314  // If the amount of energy is greater than 1 MeV, make a new grid
315  // otherwise put in the previous one.
316 
317  // If less than 1 kEV. Just skip
318  if(iStep>2&&realTotalEnergy<0.000001) continue;
319 
320  if (ecal && !usePreviousGrid)
321  {
322  status=theGrid->getPads(meanDepth[iStep]);
323  }
324  if (hcal)
325  {
326  status=theHcalHitMaker->setDepth(tt);
327  }
328  if((ecal ||hcal) && !status) continue;
329 
330  bool detailedShowerTail=false;
331  // check if a detailed treatment of the rear leakage should be applied
332  if(ecal && !usePreviousGrid)
333  {
334  detailedShowerTail=(t-dt > theGrid->getX0back());
335  }
336 
337  // The particles of the shower are processed in parallel
338  for ( unsigned int i=0; i<nPart; ++i ) {
339 
340  // double Edepo=deposit(t,a[i],b[i],dt);
341 
342  // integration of the shower profile between t-dt and t
343  double dE = (!hcal)? depositedEnergy[iStep][i]:1.-deposit(a[i],b[i],t-dt);
344 
345  // no need to do the full machinery if there is ~nothing to distribute)
346  if(dE*E[i]<0.000001) continue;
347 
348  if(detailedShowerTail)
349  {
350  myGammaGenerator->setParameters(floor(a[i]+0.5),b[i],t-dt);
351  }
352 
353  // The number of energy spots (or mips)
354  double nS = 0;
355 
356  // ECAL case : Account for photostatistics and long'al non-uniformity
357  if (ecal) {
358 
359  dE = random->poissonShoot(dE*photos[i])/photos[i];
360  double z0 = random->gaussShoot(0.,1.);
361  dE *= 1. + z0*theECAL->lightCollectionUniformity();
362 
363  // Expected spot number
364  nS = ( theNumberOfSpots[i] * gam(bSpot[i]*tt,aSpot[i])
365  * bSpot[i] * dt
366  / tgamma(aSpot[i]) );
367 
368  // Preshower : Expected number of mips + fluctuation
369  }
370  else if ( hcal ) {
371 
372  nS = ( theNumberOfSpots[i] * gam(bSpot[i]*tt,aSpot[i])
373  * bSpot[i] * dt
374  / tgamma(aSpot[i]))* theHCAL->spotFraction();
375  double nSo = nS ;
376  nS = random->poissonShoot(nS);
377  // 'Quick and dirty' fix (but this line should be better removed):
378  if( nSo > 0. && nS/nSo < 10.) dE *= nS/nSo;
379 
380 // if(true)
381 // {
382 // std::cout << " theHCAL->spotFraction = " <<theHCAL->spotFraction() <<std::endl;
383 // std::cout << " nSpot Ecal : " << nSo/theHCAL->spotFraction() << " Final " << nS << std::endl;
384 // }
385  }
386  else if ( presh1 ) {
387 
388  nS = random->poissonShoot(dE*E[i]*theLayer1->mipsPerGeV());
389  // std::cout << " dE *E[i] (1)" << dE*E[i] << " " << dE*E[i]*theLayer1->mipsPerGeV() << " "<< nS << std::endl;
390  pstot+=dE*E[i];
391  ps1tot+=dE*E[i];
392  dE = nS/(E[i]*theLayer1->mipsPerGeV());
393 
394  // E1 += dE*E[i];
395  // n1 += nS;
396  // if (presh2) { E2 += SpotEnergy; ++n2; }
397 
398  } else if ( presh2 ) {
399 
400  nS = random->poissonShoot(dE*E[i]*theLayer2->mipsPerGeV());
401  // std::cout << " dE *E[i] (2) " << dE*E[i] << " " << dE*E[i]*theLayer2->mipsPerGeV() << " "<< nS << std::endl;
402  pstot+=dE*E[i];
403  ps2tot+=dE*E[i];
404  dE = nS/(E[i]*theLayer2->mipsPerGeV());
405 
406  // E2 += dE*E[i];
407  // n2 += nS;
408 
409  }
410 
411  // myHistos->fill("h100",t,dE);
412 
413  // The lateral development parameters
414 
415  // Energy of the spots
416  double eSpot = (nS>0.) ? dE/nS : 0.;
417  double SpotEnergy=eSpot*E[i];
418 
419  if(hasPreshower&&(presh1||presh2)) thePreshower->setSpotEnergy(0.00009);
420  if(hcal)
421  {
422  SpotEnergy*=theHCAL->hOverPi();
423  theHcalHitMaker->setSpotEnergy(SpotEnergy);
424  }
425  // Poissonian fluctuations for the number of spots
426  // int nSpot = random->poissonShoot(nS);
427  int nSpot = (int)(nS+0.5);
428 
429 
430  // Fig. 11 (right) *** Does not match.
431  // myHistos->fill("h101",t,(double)nSpot/theNumberOfSpots);
432 
433  //double taui = t/T;
434  double taui = tt/Ti[i];
435  double proba = theParam->p(taui,E[i]);
436  double theRC = theParam->rC(taui,E[i]);
437  double theRT = theParam->rT(taui,E[i]);
438 
439  // Fig. 10
440  // myHistos->fill("h300",taui,theRC);
441  // myHistos->fill("h301",taui,theRT);
442  // myHistos->fill("h302",taui,proba);
443 
444  double dSpotsCore =
445  random->gaussShoot(proba*nSpot,std::sqrt(proba*(1.-proba)*nSpot));
446 
447  if(dSpotsCore<0) dSpotsCore=0;
448 
449  unsigned nSpots_core = (unsigned)(dSpotsCore+0.5);
450  unsigned nSpots_tail = ((unsigned)nSpot>nSpots_core) ? nSpot-nSpots_core : 0;
451 
452  for(unsigned icomp=0;icomp<2;++icomp)
453  {
454 
455  double theR=(icomp==0) ? theRC : theRT ;
456  unsigned ncompspots=(icomp==0) ? nSpots_core : nSpots_tail;
457 
458  RadialInterval radInterval(theR,ncompspots,SpotEnergy,random);
459  if(ecal)
460  {
461  if(icomp==0)
462  {
463  setIntervals(icomp,radInterval);
464  }
465  else
466  {
467  setIntervals(icomp,radInterval);
468  }
469  }
470  else
471  {
472  radInterval.addInterval(100.,1.);// 100% of the spots
473  }
474 
475  radInterval.compute();
476  // irad = 0 : central circle; irad=1 : outside
477 
478  unsigned nrad=radInterval.nIntervals();
479 
480  for(unsigned irad=0;irad<nrad;++irad)
481  {
482  double spote=radInterval.getSpotEnergy(irad);
483  if(ecal) theGrid->setSpotEnergy(spote);
484  if(hcal) theHcalHitMaker->setSpotEnergy(spote);
485  unsigned nradspots=radInterval.getNumberOfSpots(irad);
486  double umin=radInterval.getUmin(irad);
487  double umax=radInterval.getUmax(irad);
488  // Go for the lateral development
489  for ( unsigned ispot=0; ispot<nradspots; ++ispot )
490  {
491  double z3=random->flatShoot(umin,umax);
492  double ri=theR * std::sqrt(z3/(1.-z3)) ;
493 
494  //Fig. 12
495  /*
496  if ( 2. < t && t < 3. )
497  myHistos->fill("h401",ri,1./1000.*eSpot/dE/0.2);
498  if ( 6. < t && t < 7. )
499  myHistos->fill("h402",ri,1./1000.*eSpot/dE/0.2);
500  if ( 19. < t && t < 20. )
501  myHistos->fill("h403",ri,1./1000.*eSpot/dE/0.2);
502  */
503  // Fig. 13 (top)
504  // myHistos->fill("h400",ri,1./1000.*eSpot/0.2);
505 
506  // Generate phi
507  double phi = 2.*M_PI*random->flatShoot();
508 
509  // Add the hit in the crystal
510  // if( ecal ) theGrid->addHit(ri*theECAL->moliereRadius(),phi);
511  // Now the *moliereRadius is done in EcalHitMaker
512  if ( ecal )
513  {
514  if(detailedShowerTail)
515  {
516  // std::cout << "About to call addHitDepth " << std::endl;
517  double depth;
518  do
519  {
520  depth=myGammaGenerator->shoot();
521  }
522  while(depth>t);
523  theGrid->addHitDepth(ri,phi,depth);
524  // std::cout << " Done " << std::endl;
525  }
526  else
527  theGrid->addHit(ri,phi);
528  }
529  else if (hasPreshower&&presh1) thePreshower->addHit(ri,phi,1);
530  else if (hasPreshower&&presh2) thePreshower->addHit(ri,phi,2);
531  else if (hcal)
532  {
533  // std::cout << " About to add a spot in the HCAL" << status << std::endl;
534  theHcalHitMaker->addHit(ri,phi);
535  // std::cout << " Added a spot in the HCAL" << status << std::endl;
536  }
537  // if (ecal) E9 += SpotEnergy;
538  // if (presh1) { E1 += SpotEnergy; ++n1; }
539  // if (presh2) { E2 += SpotEnergy; ++n2; }
540 
541  Etot[i] += spote;
542  }
543  }
544  }
545  // std::cout << " Done with the step " << std::endl;
546  // The shower!
547  //myHistos->fill("h500",theSpot.z(),theSpot.perp());
548  }
549  // std::cout << " nPart " << nPart << std::endl;
550  }
551  // std::cout << " Finshed the step loop " << std::endl;
552  // myHistos->fill("h500",E1+0.7*E2,E9);
553  // myHistos->fill("h501",n1+0.7*n2,E9);
554  // myHistos->fill("h400",n1);
555  // myHistos->fill("h401",n2);
556  // myHistos->fill("h402",E9+E1+0.7*E2);
557  // if(!standalone)theGrid->printGrid();
558  double Etotal=0.;
559  for(unsigned i=0;i<nPart;++i)
560  {
561  // myHistos->fill("h10",Etot[i]);
562  Etotal+=Etot[i];
563  }
564  // myHistos->fill("h20",Etotal);
565  // if(thePreshower)
566  // std::cout << " PS " << thePreshower->layer1Calibrated() << " " << thePreshower->layer2Calibrated() << " " << thePreshower->totalCalibrated() << " " << ps1tot << " " <<ps2tot << " " << pstot << std::endl;
567 }
568 
569 
570 double
571 EMShower::gam(double x, double a) const {
572  // A stupid gamma function
573  return std::pow(x,a-1.)*std::exp(-x);
574 }
575 
576 //double
577 //EMShower::deposit(double t, double a, double b, double dt) {
578 //
579 // // The number of integration steps (about 1 / X0)
580 // int numberOfSteps = (int)dt+1;
581 //
582 // // The size if the integration step
583 // double integrationstep = dt/(double)numberOfSteps;
584 //
585 // // Half this size
586 // double halfis = 0.5*integrationstep;
587 //
588 // double dE = 0.;
589 //
590 // for(double tt=t-dt+halfis;tt<t;tt+=integrationstep) {
591 //
592 // // Simpson integration over each of these steps
593 // dE += gam(b*(tt-halfis),a)
594 // + 4.*gam(b* tt ,a)
595 // + gam(b*(tt+halfis),a);
596 //
597 // }
598 //
599 // // Normalization
600 // dE *= b*integrationstep/tgamma(a)/6.;
601 //
602 // // There we go.
603 // return dE;
604 //}
605 
606 double
607 EMShower::deposit(double t, double a, double b, double dt) {
608  myIncompleteGamma.a().setValue(a);
609  double b1=b*(t-dt);
610  double b2=b*t;
611  double result = 0.;
612  double rb1=(b1!=0.) ? myIncompleteGamma(b1) : 0.;
613  double rb2=(b2!=0.) ? myIncompleteGamma(b2) : 0.;
614  result = (rb2-rb1);
615  return result;
616 }
617 
618 
619 void EMShower::setIntervals(unsigned icomp, RadialInterval& rad)
620 {
621  // std::cout << " Got the pointer " << std::endl;
622  const std::vector<double>& myValues((icomp)?theParam->getTailIntervals():theParam->getCoreIntervals());
623  // std::cout << " Got the vector " << myValues.size () << std::endl;
624  unsigned nvals=myValues.size()/2;
625  for(unsigned iv=0;iv<nvals;++iv)
626  {
627  // std::cout << myValues[2*iv] << " " << myValues[2*iv+1] <<std::endl;
628  rad.addInterval(myValues[2*iv],myValues[2*iv+1]);
629  }
630 }
631 
633 {
634  if(myPresh!=NULL)
635  {
636  thePreshower = myPresh;
637  hasPreshower=true;
638  }
639 }
640 
641 
642 void EMShower::setHcal(HcalHitMaker * const myHcal)
643 {
644  theHcalHitMaker = myHcal;
645 }
646 
647 double
648 EMShower::deposit( double a, double b, double t) {
649  // std::cout << " Deposit " << std::endl;
650  myIncompleteGamma.a().setValue(a);
651  double b2=b*t;
652  double result = 0.;
653  if(fabs(b2) < 1.e-9 ) b2 = 1.e-9;
654  result=myIncompleteGamma(b2);
655  // std::cout << " deposit t = " << t << " " << result <<std::endl;
656  return result;
657 
658 }
void setSpotEnergy(double e)
Set the spot energy.
Definition: HcalHitMaker.h:28
double getX0back() const
Definition: EcalHitMaker.h:109
float dt
Definition: AMPTWrapper.h:126
int i
Definition: DBlmapReader.cc:9
double ps2TotalX0() const
total number of X0 in the PS (Layer2).
Definition: EcalHitMaker.h:65
std::vector< const RawParticle * > *const thePart
Definition: EMShower.h:92
std::vector< double > theNumberOfSpots
Definition: EMShower.h:96
EMShower(const RandomEngine *engine, GammaFunctionGenerator *gamma, EMECALShowerParametrization *const myParam, std::vector< const RawParticle * > *const myPart, EcalHitMaker *const myGrid=NULL, PreshowerHitMaker *const myPreshower=NULL)
Definition: EMShower.cc:17
double sigmaLnT(double lny) const
const HCALProperties * hcalProperties() const
void prepareSteps()
Computes the steps before the real compute.
Definition: EMShower.cc:123
std::vector< double > maximumOfShower
Definition: EMShower.h:111
bool addHit(double r, double phi, unsigned layer=0)
double meanAlphaSpot(double alpha) const
void setSpotEnergy(double e)
Definition: EcalHitMaker.h:117
std::vector< double > aSpot
Definition: EMShower.h:105
unsigned getNumberOfSpots(unsigned i) const
Number of spots in a given interval.
list step
Definition: launcher.py:15
bool addHit(double r, double phi, unsigned layer=0)
double deposit(double t, double a, double b, double dt)
Definition: EMShower.cc:607
double gam(double x, double a) const
Definition: EMShower.cc:571
const HCALProperties * theHCAL
Definition: EMShower.h:87
void setPreshower(PreshowerHitMaker *const myPresh)
set the preshower address
Definition: EMShower.cc:632
#define NULL
Definition: scimark2.h:8
double rC(double tau, double E) const
Exp< T >::type exp(const T &t)
Definition: Exp.h:22
const ECALProperties * theECAL
Definition: EMShower.h:86
double ps2eeTotalX0() const
Definition: EcalHitMaker.h:68
TRandom random
Definition: MVATrainer.cc:138
void setIntervals(unsigned icomp, RadialInterval &rad)
Definition: EMShower.cc:619
const std::vector< double > & getTailIntervals() const
void compute()
Compute the shower longitudinal and lateral development.
Definition: EMShower.cc:244
const std::vector< double > & getCoreIntervals() const
double gaussShoot(double mean=0.0, double sigma=1.0) const
Definition: RandomEngine.h:37
std::vector< double > Etot
Definition: EMShower.h:97
bool stepsCalculated
Definition: EMShower.h:123
double spotFraction() const
Spot fraction wrt ECAL.
double hOverPi() const
PreshowerHitMaker * thePreshower
Definition: EMShower.h:129
std::vector< std::vector< double > > depositedEnergy
Definition: EMShower.h:112
double ecalTotalX0() const
in the ECAL
Definition: EcalHitMaker.h:71
Steps steps
Definition: EMShower.h:121
bool addHitDepth(double r, double phi, double depth=-1)
T sqrt(T t)
Definition: SSEVec.h:28
unsigned int poissonShoot(double mean) const
Definition: RandomEngine.h:44
tuple result
Definition: query.py:137
double getUmin(unsigned i) const
Lower limit of the argument in the radius generator.
double innerDepth
Definition: EMShower.h:114
HcalHitMaker * theHcalHitMaker
Definition: EMShower.h:132
double hcalTotalX0() const
in the HCAL
Definition: EcalHitMaker.h:77
unsigned int nPart
Definition: EMShower.h:93
std::vector< double > meanDepth
Definition: EMShower.h:113
double rT(double tau, double E) const
void setParameters(double a, double b, double xm)
The parameters must be set before shooting.
unsigned int offset(bool)
std::vector< double > photos
Definition: EMShower.h:99
const PreshowerLayer1Properties * layer1Properties() const
void setSpotEnergy(double e)
double correlationAlphaT(double lny) const
const ECALProperties * ecalProperties() const
#define M_PI
Definition: BFit3D.cc:3
unsigned nIntervals() const
Number of intervals.
Log< T >::type log(const T &t)
Definition: Log.h:22
bool hasPreshower
Definition: EMShower.h:135
double mipsPerGeV() const
Number of Mips/GeV [Default : 41.7 Mips/GeV or 24 MeV/Mips].
double mipsPerGeV() const
Number of Mips/GeV [Default : 59.5 Mips/GeV or 0.7*24 MeV/Mips].
double criticalEnergy() const
Critical energy in GeV (2.66E-3*(x0*Z/A)^1.1)
double globalMaximum
Definition: EMShower.h:116
double p(double tau, double E) const
double b
Definition: hdecay.h:120
const PreshowerLayer2Properties * layer2Properties() const
const PreshowerLayer2Properties * theLayer2
Definition: EMShower.h:89
double flatShoot(double xmin=0.0, double xmax=1.0) const
Definition: RandomEngine.h:30
bool getPads(double depth, bool inCm=false)
double meanLnAlpha(double lny) const
virtual double lightCollectionEfficiency() const =0
Light Collection efficiency.
const PreshowerLayer1Properties * theLayer1
Definition: EMShower.h:88
std::vector< double > a
Definition: EMShower.h:101
double a
Definition: hdecay.h:121
double outerDepth
Definition: EMShower.h:114
double meanAlpha(double lny) const
virtual double lightCollectionUniformity() const =0
Light Collection uniformity.
EMECALShowerParametrization *const theParam
Definition: EMShower.h:83
EcalHitMaker * theGrid
Definition: EMShower.h:126
GammaFunctionGenerator * myGammaGenerator
Definition: EMShower.h:145
double sigmaLnAlpha(double lny) const
std::vector< double > Ti
Definition: EMShower.h:103
std::vector< double > TSpot
Definition: EMShower.h:104
Definition: DDAxes.h:10
double getSpotEnergy(unsigned i) const
Spot energy in a given interval.
unsigned nSteps
Definition: EMShower.h:122
Genfun::IncompleteGamma myIncompleteGamma
Definition: EMShower.h:139
tuple status
Definition: ntuplemaker.py:245
std::vector< double > b
Definition: EMShower.h:102
double ps1TotalX0() const
Definition: EcalHitMaker.h:62
double totalEnergy
Definition: EMShower.h:118
std::vector< double > E
Definition: EMShower.h:98
const RandomEngine * random
Definition: EMShower.h:142
bool addHit(double r, double phi, unsigned layer=0)
add the hit in the HCAL in local coordinates
Definition: HcalHitMaker.cc:28
long double T
double getUmax(unsigned i) const
Upper limit of the argument in the radius generator.
virtual double photoStatistics() const =0
Photostatistics (photons/GeV) in the homegeneous material.
double x0DepthOffset() const
get the offset (e.g the number of X0 after which the shower starts)
Definition: EcalHitMaker.h:59
std::pair< unsigned int, double > Step
Definition: EMShower.h:32
Power< A, B >::type pow(const A &a, const B &b)
Definition: Power.h:40
bool setDepth(double, bool inCm=false)
set the depth in X0 or Lambda0 units depending on showerType
double totalX0() const
Definition: EcalHitMaker.h:53
void addInterval(double, double)
void setHcal(HcalHitMaker *const myHcal)
set the HCAL address
Definition: EMShower.cc:642
std::vector< double > bSpot
Definition: EMShower.h:106
Definition: DDAxes.h:10