CMS 3D CMS Logo

HcalTB02Analysis.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: HcalTestBeam
4 // Class : HcalTB02Analysis
5 //
6 // Implementation:
7 // Main analysis class for Hcal Test Beam 2002 Analysis
8 //
9 // Original Author:
10 // Created: Sun May 21 10:14:34 CEST 2006
11 //
12 
13 // system include files
14 #include <cmath>
15 #include <iostream>
16 #include <iomanip>
17 #include <memory>
18 #include <map>
19 #include <vector>
20 #include <string>
21 
22 // user include files
23 // to retreive hits
33 
38 
42 
43 #include "G4HCofThisEvent.hh"
44 #include "G4SDManager.hh"
45 #include "G4Step.hh"
46 #include "G4Track.hh"
47 #include "G4ThreeVector.hh"
48 #include "G4VProcess.hh"
49 
50 #include <CLHEP/Random/RandGaussQ.h>
51 #include <CLHEP/Random/Randomize.h>
52 #include <CLHEP/Units/SystemOfUnits.h>
53 #include <CLHEP/Units/PhysicalConstants.h>
54 
55 using CLHEP::GeV;
56 using CLHEP::twopi;
57 
58 //#define EDM_ML_DEBUG
59 
60 namespace CLHEP {
61  class HepRandomEngine;
62 }
63 
64 class HcalTB02Analysis : public SimProducer, public Observer<const BeginOfEvent*>, public Observer<const EndOfEvent*> {
65 public:
67  HcalTB02Analysis(const HcalTB02Analysis&) = delete; // stop default
68  const HcalTB02Analysis& operator=(const HcalTB02Analysis&) = delete;
69  ~HcalTB02Analysis() override;
70 
71  void produce(edm::Event&, const edm::EventSetup&) override;
72 
73 private:
74  // observer methods
75  void update(const BeginOfEvent* evt) override;
76  void update(const EndOfEvent* evt) override;
77 
79  void clear();
80  void finish();
81 
82 private:
83  // Private Tuples
84  std::unique_ptr<HcalTB02Histo> histo;
85 
86  // to read from parameter set
88  const bool hcalOnly;
89  const std::vector<std::string> names;
90 
91  //To be saved
92  std::map<int, float> energyInScints, energyInCrystals;
93  std::map<int, float> primaries;
98  int maxTime;
103 };
104 
105 //
106 // constructors and destructor
107 //
108 
110  : m_Anal(p.getParameter<edm::ParameterSet>("HcalTB02Analysis")),
111  hcalOnly(m_Anal.getUntrackedParameter<bool>("HcalClusterOnly", true)),
112  names(m_Anal.getParameter<std::vector<std::string> >("Names")) {
113  produces<HcalTB02HistoClass>();
114 
115  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis:: Initialised as observer of "
116  << "BeginOfJob/BeginOfEvent/EndOfEvent with "
117  << "Parameter values:\n \thcalOnly = " << hcalOnly;
118 
119  histo = std::make_unique<HcalTB02Histo>(m_Anal);
120 }
121 
123 
124 //
125 // member functions
126 //
127 
129  std::unique_ptr<HcalTB02HistoClass> product(new HcalTB02HistoClass);
130  fillEvent(*product);
131  e.put(std::move(product));
132 }
133 
135 #ifdef EDM_ML_DEBUG
136  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis: =====> Begin of event = " << (*evt)()->GetEventID();
137 #endif
138  clear();
139 }
140 
142  CLHEP::HepRandomEngine* engine = G4Random::getTheEngine();
143  CLHEP::RandGaussQ randGauss(*engine);
144 
145  // Look for the Hit Collection
146 #ifdef EDM_ML_DEBUG
147  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis::Fill event " << (*evt)()->GetEventID();
148 #endif
149  // access to the G4 hit collections
150  G4HCofThisEvent* allHC = (*evt)()->GetHCofThisEvent();
151  int ihit = 0;
152 
153  // HCAL
154  std::string sd = names[0];
155  int HCHCid = G4SDManager::GetSDMpointer()->GetCollectionID(sd);
156  CaloG4HitCollection* theHCHC = (CaloG4HitCollection*)allHC->GetHC(HCHCid);
157 #ifdef EDM_ML_DEBUG
158  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis :: Hit Collection for " << sd << " of ID " << HCHCid
159  << " is obtained at " << theHCHC;
160 #endif
161  int nentries = 0;
162  nentries = theHCHC->entries();
163  if (nentries == 0)
164  return;
165 
166  int xentries = 0;
167  int XTALSid = 0;
168  CaloG4HitCollection* theXTHC = nullptr;
169 
170  if (!hcalOnly) {
171  // XTALS
172  sd = names[1];
173  XTALSid = G4SDManager::GetSDMpointer()->GetCollectionID(sd);
174  theXTHC = (CaloG4HitCollection*)allHC->GetHC(XTALSid);
175 #ifdef EDM_ML_DEBUG
176  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis :: Hit Collection for " << sd << " of ID " << XTALSid
177  << " is obtained at " << theXTHC;
178 #endif
179  xentries = theXTHC->entries();
180  if (xentries == 0)
181  return;
182  }
183 
184 #ifdef EDM_ML_DEBUG
185  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis :: There are " << nentries << " HCal hits, and" << xentries
186  << " xtal hits";
187 #endif
188  float ETot = 0., xETot = 0.;
189  int scintID = 0, xtalID = 0;
190 
191  // HCAL
192  std::unique_ptr<HcalTB02HcalNumberingScheme> org(new HcalTB02HcalNumberingScheme());
193 
194  if (HCHCid >= 0 && theHCHC != nullptr) {
195  for (ihit = 0; ihit < nentries; ihit++) {
196  CaloG4Hit* aHit = (*theHCHC)[ihit];
197  scintID = aHit->getUnitID();
198  int layer = org->getlayerID(scintID);
199  float enEm = aHit->getEM();
200  float enhad = aHit->getHadr();
201 
202  if (layer == 0) {
203  enEm = enEm / 2.;
204  enhad = enhad / 2.;
205  }
206 
207  energyInScints[scintID] += enEm + enhad;
208  primaries[aHit->getTrackID()] += enEm + enhad;
209  float time = aHit->getTimeSliceID();
210  if (time > maxTime)
211  maxTime = static_cast<int>(time);
212  histo->fillAllTime(time);
213  }
214 
215  //
216  // Profile
217  //
218 
219  float TowerEne[8][18], TowerEneCF[8][18], LayerEne[19], EnRing[100];
220  for (int iphi = 0; iphi < 8; iphi++) {
221  for (int jeta = 0; jeta < 18; jeta++) {
222  TowerEne[iphi][jeta] = 0.;
223  TowerEneCF[iphi][jeta] = 0.;
224  }
225  }
226 
227  for (int ilayer = 0; ilayer < 19; ilayer++)
228  LayerEne[ilayer] = 0.;
229  for (int iring = 0; iring < 100; iring++)
230  EnRing[iring] = 0.;
231 
232  for (std::map<int, float>::iterator is = energyInScints.begin(); is != energyInScints.end(); is++) {
233  ETot = (*is).second;
234 
235  int layer = org->getlayerID((*is).first);
236 
237  if ((layer != 17) && (layer != 18)) {
238  float eta = org->getetaID((*is).first);
239  float phi = org->getphiID((*is).first);
240 
241  SEnergy += ETot;
242  int iphi = static_cast<int>(phi);
243  int ieta = static_cast<int>(eta);
244  TowerEne[iphi][ieta] += ETot;
245 
246  TowerEneCF[iphi][ieta] += ETot * (1. + 0.1 * randGauss.fire());
247  double dR = 0.08727 * std::sqrt((eta - 8.) * (eta - 8.) + (phi - 3.) * (phi - 3.));
248  EnRing[static_cast<int>(dR / 0.01)] += ETot;
249  }
250 
251  LayerEne[layer] += ETot;
252  }
253 
254  for (int ilayer = 0; ilayer < 19; ilayer++) {
255  histo->fillProfile(ilayer, LayerEne[ilayer] / GeV);
256  }
257 
258  for (int iring = 0; iring < 100; iring++)
259  histo->fillTransProf(0.01 * iring + 0.005, EnRing[iring] / GeV);
260 
261  for (int iphi = 0; iphi < 8; iphi++) {
262  for (int jeta = 0; jeta < 18; jeta++) {
263  SEnergyN += TowerEneCF[iphi][jeta] + 3. * randGauss.fire(); // QGSP
264 
265  double Rand = 3. * randGauss.fire(); // QGSP
266 
267  if ((iphi >= 0) && (iphi < 7)) {
268  if ((jeta >= 5) && (jeta < 12)) {
269  E7x7Matrix += TowerEne[iphi][jeta];
270  E7x7MatrixN += TowerEneCF[iphi][jeta] + Rand;
271 
272  if ((iphi >= 1) && (iphi < 6)) {
273  if ((jeta >= 6) && (jeta < 11)) {
274  E5x5Matrix += TowerEne[iphi][jeta];
275  E5x5MatrixN += TowerEneCF[iphi][jeta] + Rand;
276  }
277  }
278  }
279  }
280  }
281  }
282 
283  //
284  // Find Primary info:
285  //
286  int trackID = 0;
287  G4PrimaryParticle* thePrim = nullptr;
288  G4int nvertex = (*evt)()->GetNumberOfPrimaryVertex();
289 #ifdef EDM_ML_DEBUG
290  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis :: Event has " << nvertex << " vertex";
291 #endif
292  if (nvertex == 0)
293  edm::LogWarning("HcalTBSim") << "HcalTB02Analysis:: End Of Event "
294  << "ERROR: no vertex";
295 
296  for (int i = 0; i < nvertex; i++) {
297  G4PrimaryVertex* avertex = (*evt)()->GetPrimaryVertex(i);
298  if (avertex == nullptr) {
299  edm::LogWarning("HcalTBSim") << "HcalTB02Analysis:: End Of Event "
300  << "ERROR: pointer to vertex = 0";
301  } else {
302 #ifdef EDM_ML_DEBUG
303  int npart = avertex->GetNumberOfParticle();
304  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis::Vertex number :" << i << " with " << npart << " particles";
305 #endif
306  if (thePrim == nullptr)
307  thePrim = avertex->GetPrimary(trackID);
308  }
309  }
310 
311  double px = 0., py = 0., pz = 0.;
312 
313  if (thePrim != nullptr) {
314  px = thePrim->GetPx();
315  py = thePrim->GetPy();
316  pz = thePrim->GetPz();
317  pInit = std::sqrt(pow(px, 2.) + pow(py, 2.) + pow(pz, 2.));
318  if (pInit == 0) {
319  edm::LogWarning("HcalTBSim") << "HcalTB02Analysis:: End Of Event "
320  << " ERROR: primary has p=0 ";
321  } else {
322  float costheta = pz / pInit;
323  float theta = acos(std::min(std::max(costheta, float(-1.)), float(1.)));
324  eta = -std::log(std::tan(theta / 2));
325  if (px != 0)
326  phi = std::atan(py / px);
327  }
328  particleType = thePrim->GetPDGcode();
329  } else {
330 #ifdef EDM_ML_DEBUG
331  edm::LogVerbatim("HcalTBSim") << "HcalTB02Analysis:: End Of Event ERROR: could not find primary ";
332 #endif
333  }
334 
335  CaloG4Hit* firstHit = (*theHCHC)[0];
336  incidentEnergy = (firstHit->getIncidentEnergy() / GeV);
337 
338  } // number of Hits > 0
339 
340  if (!hcalOnly) {
341  // XTALS
342 
343  if (XTALSid >= 0 && theXTHC != nullptr) {
344  for (int xihit = 0; xihit < xentries; xihit++) {
345  CaloG4Hit* xaHit = (*theXTHC)[xihit];
346 
347  float xenEm = xaHit->getEM();
348  float xenhad = xaHit->getHadr();
349  xtalID = xaHit->getUnitID();
350 
351  energyInCrystals[xtalID] += xenEm + xenhad;
352  }
353 
354  float xCrysEne[7][7];
355  for (int irow = 0; irow < 7; irow++) {
356  for (int jcol = 0; jcol < 7; jcol++) {
357  xCrysEne[irow][jcol] = 0.;
358  }
359  }
360 
361  for (std::map<int, float>::iterator is = energyInCrystals.begin(); is != energyInCrystals.end(); is++) {
362  int xtalID = (*is).first;
363  xETot = (*is).second;
364 
365  int irow = static_cast<int>(xtalID / 100.);
366  int jcol = static_cast<int>(xtalID - 100. * irow);
367 
368  xSEnergy += xETot;
369  xCrysEne[irow][jcol] = xETot;
370 
371  float dR = std::sqrt(0.01619 * 0.01619 * (jcol - 3) * (jcol - 3) + 0.01606 * 0.01606 * (irow - 3) * (irow - 3));
372  histo->fillTransProf(dR, xETot * 1.05);
373 
374  if ((irow > 0) && (irow < 6)) {
375  if ((jcol > 0) && (jcol < 6)) {
376  xE5x5Matrix += xCrysEne[irow][jcol];
377  xE5x5MatrixN += xCrysEne[irow][jcol] + 108.5 * randGauss.fire();
378 
379  if ((irow > 1) && (irow < 5)) {
380  if ((jcol > 1) && (jcol < 5)) {
381  xE3x3Matrix += xCrysEne[irow][jcol];
382  xE3x3MatrixN += xCrysEne[irow][jcol] + 108.5 * randGauss.fire();
383  }
384  }
385  }
386  }
387  }
388 
389  if (!hcalOnly) {
390  // assert(theXTHC);
391  if (theXTHC != nullptr) {
392  CaloG4Hit* xfirstHit = (*theXTHC)[0];
393  xIncidentEnergy = xfirstHit->getIncidentEnergy() / GeV;
394  }
395  }
396 
397  } // number of Hits > 0
398  }
399 
400  int iEvt = (*evt)()->GetEventID();
401  if (iEvt < 10)
402  edm::LogVerbatim("HcalTBSim") << " Event " << iEvt;
403  else if ((iEvt < 100) && (iEvt % 10 == 0))
404  edm::LogVerbatim("HcalTBSim") << " Event " << iEvt;
405  else if ((iEvt < 1000) && (iEvt % 100 == 0))
406  edm::LogVerbatim("HcalTBSim") << " Event " << iEvt;
407  else if ((iEvt < 10000) && (iEvt % 1000 == 0))
408  edm::LogVerbatim("HcalTBSim") << " Event " << iEvt;
409 }
410 
412  //Beam information
413  product.set_Nprim(float(primaries.size()));
414  product.set_partType(particleType);
415  product.set_Einit(pInit / GeV);
416  product.set_eta(eta);
417  product.set_phi(phi);
418  product.set_Eentry(incidentEnergy);
419 
420  //Calorimeter energy
421  product.set_ETot(SEnergy / GeV);
422  product.set_E7x7(E7x7Matrix / GeV);
423  product.set_E5x5(E5x5Matrix / GeV);
424  product.set_ETotN(SEnergyN / GeV);
425  product.set_E7x7N(E7x7MatrixN / GeV);
426  product.set_E5x5N(E5x5MatrixN / GeV);
427  product.set_NUnit(float(energyInScints.size()));
428  product.set_Ntimesli(float(maxTime));
429 
430  //crystal information
431  product.set_xEentry(xIncidentEnergy);
432  product.set_xNUnit(float(energyInCrystals.size()));
433  product.set_xETot(xSEnergy / GeV);
434  product.set_xETotN(xSEnergyN / GeV);
435  product.set_xE5x5(xE5x5Matrix / GeV);
436  product.set_xE3x3(xE3x3Matrix / GeV);
437  product.set_xE5x5N(xE5x5MatrixN / GeV);
438  product.set_xE3x3N(xE3x3MatrixN / GeV);
439 }
440 
442  primaries.clear();
443  particleType = 0;
444  pInit = eta = phi = incidentEnergy = 0;
445 
447  E7x7MatrixN = E5x5MatrixN = 0;
448  energyInScints.clear();
449  maxTime = 0;
450 
451  xIncidentEnergy = 0;
452  energyInCrystals.clear();
455 }
456 
458  /*
459  //Profile
460  std::ofstream oFile;
461  oFile.open("profile.dat");
462  float st[19] = {0.8,
463  0.4, 0.4, 0.4, 0.4, 0.4,
464  0.4, 0.4, 0.4, 0.4, 0.4,
465  0.4, 0.4, 0.4, 0.4, 0.4,
466  0.8, 1.0, 1.0};
467 
468  //cm of material (brass) in front of scintillator layer i:
469 
470  float w[19] = {7.45, //iron !
471  6.00, 6.00, 6.00, 6.00, 6.00, //brass
472  6.00, 6.00, 6.00, 6.00, 6.60, //brass
473  6.60, 6.60, 6.60, 6.60, 6.60, //brass
474  8.90, 20.65, 19.5}; //brass,iron !
475 
476  for (int ilayer = 0; ilayer<19; ilayer++) {
477 
478  // Histogram mean and sigma calculated from the ROOT histos
479  edm::LogVerbatim("HcalTBSim") << "Layer number: " << ilayer << " Mean = "
480  << histo->getMean(ilayer) << " sigma = "
481  << histo->getRMS(ilayer) << " LThick= "
482  << w[ilayer] << " SThick= " << st[ilayer];
483 
484  oFile << ilayer << " " << histo->getMean(ilayer) << " "
485  << histo->getRMS(ilayer) << " " << w[ilayer] << " " << st[ilayer]
486  << std::endl;
487 
488  }
489  oFile.close();
490  */
491 }
492 
void set_xE3x3N(float v)
Log< level::Info, true > LogVerbatim
void set_E5x5N(float v)
void set_Ntimesli(float v)
int getTrackID() const
Definition: CaloG4Hit.h:64
void set_NUnit(float v)
#define DEFINE_SIMWATCHER(type)
void set_Eentry(float v)
std::map< int, float > energyInScints
void set_xEentry(float v)
void set_xETotN(float v)
void set_Nprim(float v)
void set_E7x7(float v)
~HcalTB02Analysis() override
double getEM() const
Definition: CaloG4Hit.h:55
void set_ETotN(float v)
double npart
Definition: HydjetWrapper.h:48
void set_Einit(float v)
const HcalTB02Analysis & operator=(const HcalTB02Analysis &)=delete
void produce(edm::Event &, const edm::EventSetup &) override
void set_xETot(float v)
void set_E7x7N(float v)
const std::string names[nVars_]
double getHadr() const
Definition: CaloG4Hit.h:58
void fillEvent(HcalTB02HistoClass &)
const edm::ParameterSet m_Anal
void set_xE3x3(float v)
HcalTB02Analysis(const edm::ParameterSet &p)
void update(const BeginOfEvent *evt) override
This routine will be called when the appropriate signal arrives.
void set_xE5x5N(float v)
std::unique_ptr< HcalTB02Histo > histo
T sqrt(T t)
Definition: SSEVec.h:23
Tan< T >::type tan(const T &t)
Definition: Tan.h:22
std::map< int, float > primaries
const std::vector< std::string > names
int getTimeSliceID() const
Definition: CaloG4Hit.h:68
void set_E5x5(float v)
void set_partType(float v)
uint32_t getUnitID() const
Definition: CaloG4Hit.h:66
HLT enums.
G4THitsCollection< CaloG4Hit > CaloG4HitCollection
void set_ETot(float v)
void set_xE5x5(float v)
Log< level::Warning, false > LogWarning
double getIncidentEnergy() const
Definition: CaloG4Hit.h:61
Power< A, B >::type pow(const A &a, const B &b)
Definition: Power.h:29
def move(src, dest)
Definition: eostools.py:511
std::map< int, float > energyInCrystals
void set_xNUnit(float v)