CMS 3D CMS Logo

G4StepStatistics.h
Go to the documentation of this file.
1 #ifndef HelpfulWatchers_G4StepStatistics_h
2 #define HelpfulWatchers_G4StepStatistics_h
3 // -*- C++ -*-
4 //
5 // Package: HelpfulWatchers
6 // Class : SimTracer
7 //
16 //
17 // Original Author:
18 // Created: Tue Nov 22 16:41:33 EST 2005
19 //
20 
21 // system include files
22 #include <iostream>
23 
24 // user include files
26 #include "G4ParticleDefinition.hh"
27 #include "G4Step.hh"
28 #include "G4VProcess.hh"
33 #include <map>
34 
35 #include <TClonesArray.h>
36 #include <TFile.h>
37 #include <TROOT.h>
38 #include <TString.h>
39 #include <TTree.h>
40 #include <TVector.h>
41 #include <TObjString.h>
42 
43 // forward declarations
44 class DDDWorld;
45 class BeginOfJob;
46 class BeginOfRun;
47 class BeginOfEvent;
48 class BeginOfTrack;
49 class G4Step;
50 
51 class EndOfRun;
52 class EndOfEvent;
53 class EndOfTrack;
54 
55 // Define a class StepID
56 class StepID {
57 private:
58  // G4 Region
59  G4String theG4RegionName;
60  // G4 Physical Process
61  G4String theG4ProcessName;
62  // Particle PDG ID
64 
65 public:
66  // Constructor using G4Step
67  StepID(const G4Step *theG4Step)
68  : theG4RegionName("UNDEFINED"),
69  theG4ProcessName("UNDEFINED"),
70  theParticlePDGID(theG4Step->GetTrack()->GetDefinition()->GetPDGEncoding()) {
71  std::cout << "Start" << std::endl;
72  if (theG4Step->GetPreStepPoint()->GetPhysicalVolume()) {
73  theG4RegionName = theG4Step->GetPreStepPoint()->GetPhysicalVolume()->GetLogicalVolume()->GetRegion()->GetName();
74  }
75  std::cout << "Physical Volume" << std::endl;
76  if (theG4Step->GetPreStepPoint()->GetProcessDefinedStep()) {
77  theG4ProcessName = theG4Step->GetPreStepPoint()->GetProcessDefinedStep()->GetProcessName();
78  }
79  std::cout << "Process Name" << std::endl;
80  }
81 
82  // Getters
83  G4String GetRegionName() const { return theG4RegionName; }
84  G4String GetProcessName() const { return theG4ProcessName; }
85  G4int GetParticlePDGID() const { return theParticlePDGID; }
86 
87  // Comparison Operators (necessary in order to use StepID as a key in a map)
88  bool operator==(const StepID &id) const {
89  return (strcmp(theG4RegionName, id.GetRegionName()) == 0 && strcmp(theG4ProcessName, id.GetProcessName()) == 0 &&
91  ? true
92  : false;
93  }
94 
95  bool operator<(const StepID &id) const {
96  if (theParticlePDGID != id.GetParticlePDGID()) {
97  return (theParticlePDGID > id.GetParticlePDGID());
98  } else if (strcmp(theG4RegionName, id.GetRegionName()) != 0) {
99  return strcmp(theG4RegionName, id.GetRegionName()) > 0 ? true : false;
100  } else if (strcmp(theG4ProcessName, id.GetProcessName()) != 0) {
101  return strcmp(theG4ProcessName, id.GetProcessName()) > 0 ? true : false;
102  } else { // The case in which they are all equal!
103  return false;
104  }
105  }
106 
107  bool operator>(const StepID &id) const {
108  if (theParticlePDGID != id.GetParticlePDGID()) {
109  return (theParticlePDGID < id.GetParticlePDGID());
110  } else if (strcmp(theG4RegionName, id.GetRegionName()) != 0) {
111  return strcmp(theG4RegionName, id.GetRegionName()) < 0 ? true : false;
112  } else if (strcmp(theG4ProcessName, id.GetProcessName()) != 0) {
113  return strcmp(theG4ProcessName, id.GetProcessName()) < 0 ? true : false;
114  } else { // The case in which they are all equal!
115  return false;
116  }
117  }
118 };
119 
120 #define OBSERVES(type) \
121 public \
122  Observer<const type *>
123 #define UPDATE(type) \
124  void update(const type *) override { std::cout << "++ signal " #type << std::endl; }
126  OBSERVES(DDDWorld),
127  OBSERVES(BeginOfJob),
128  OBSERVES(BeginOfRun),
129  OBSERVES(BeginOfEvent),
130  OBSERVES(BeginOfTrack),
131  OBSERVES(G4Step),
132  OBSERVES(EndOfRun),
133  OBSERVES(EndOfEvent),
134  OBSERVES(EndOfTrack) {
135 public:
137  : m_verbose(pSet.getUntrackedParameter<bool>("verbose", false)), Event(0) {
138  // Adding TFile Service output
139  G4StepTree = fs->make<TTree>("G4StepTree", "G4Step Tree ");
140  G4StepTree->Branch("Event", &Event, "Event/I");
141  G4StepTree->Branch("PDGID", &PDGID, "PDGID[100000]/I");
142  Region = new TClonesArray("TObjString", 100000);
143  G4StepTree->Branch("Region", &Region);
144  Process = new TClonesArray("TObjString", 100000);
145  G4StepTree->Branch("Process", &Process);
146  G4StepTree->Branch("G4StepFreq", &G4StepFreq, "G4StepFreq[100000]/I");
147  }
151  // void update(const BeginOfRun* iRun) {
152  // std::cout <<"++ signal BeginOfRun " <<std::endl;
153  //}
156  void update(const G4Step *iStep) override {
157  std::cout << "++ signal G4Step ";
158  // Dump the relevant information from the G4 step in the object mysteptest
159  StepID mysteptest(iStep);
160  // Add the StepID to the map, or increment if it already exists:
161  if (G4StatsMap.find(mysteptest) == G4StatsMap.end()) {
162  // Allocating new memory for a pointer to associate with the key
163  // mysteptest in our map. Initializing it to 1,will be incremented working
164  // on the value of the pointer.
165  unsigned int *MyValue = new unsigned int(1);
166  // Inserting the new key,value pair
167  G4StatsMap.insert(std::make_pair(mysteptest, MyValue));
168  } else {
169  // Incrementing the value of the pointer by 1
170  *G4StatsMap[mysteptest] = *G4StatsMap[mysteptest] + 1;
171  }
172 
173  // If the verbose flag is set, then dump the information
174  if (m_verbose) {
175  std::cout << " StepID RegionName: " << mysteptest.GetRegionName();
176  std::cout << " StepID ProcessName: " << mysteptest.GetProcessName();
177  std::cout << " StepID ParticlePDGID: " << mysteptest.GetParticlePDGID();
178  }
179  std::cout << std::endl;
180  }
181  // UPDATE(G4Step)
183  // void update(const EndOfRun* iRun) {
184  // std::cout <<"++ signal EndOfRun " <<std::endl;
185  //}
186 
187  // UPDATE(EndOfEvent)
188  void update(const EndOfEvent *iRun) override {
189  std::cout << "++ signal EndOfEvent " << std::endl;
190  Event++;
191 
192  // Dumping the map in the log if verbose is chosen:
193  if (m_verbose) {
194  std::cout << " G4StatsMap size is: " << G4StatsMap.size() << std::endl;
195  }
196  int index(0);
197  for (std::map<const StepID, unsigned int *>::const_iterator step = G4StatsMap.begin(); step != G4StatsMap.end();
198  ++step, ++index) {
199  if (m_verbose) {
200  std::cout << " G4StatsMap step is: " << step->first.GetRegionName() << " " << step->first.GetProcessName()
201  << " " << step->first.GetParticlePDGID(); //<<" "<<step->first.GetTrackID() ;
202  std::cout << " Number of such steps: " << *step->second << std::endl;
203  }
204  // Rolling the map into 5 "arrays", containing the StepID information and
205  // the G4Step statistics
206  PDGID[index] = step->first.GetParticlePDGID();
207  new ((*Region)[index]) TObjString(step->first.GetRegionName());
208  new ((*Process)[index]) TObjString(step->first.GetProcessName());
209  G4StepFreq[index] = *step->second;
210  }
211 
212  G4StepTree->Fill();
213  }
215 
216 private:
217  bool m_verbose;
218 
219  // Adding the G4StatsMap to keep track of statistics in terms of step
220  // information...
221  std::map<const StepID, unsigned int *> G4StatsMap;
223  TTree *G4StepTree;
224  unsigned int Event;
225  Int_t PDGID[100000];
226  TClonesArray *Region;
227  TClonesArray *Process;
228  Int_t G4StepFreq[100000];
229 };
230 
231 #endif
void update(const DDDWorld *) override
This routine will be called when the appropriate signal arrives.
bool operator<(const StepID &id) const
Int_t G4StepFreq[100000]
G4StepStatistics(const edm::ParameterSet &pSet)
bool operator>(const StepID &id) const
G4String theG4RegionName
unsigned int Event
StepID(const G4Step *theG4Step)
G4String theG4ProcessName
TEMPL(T2) struct Divides void
Definition: Factorize.h:24
G4String GetRegionName() const
G4int theParticlePDGID
bool operator==(const StepID &id) const
Int_t PDGID[100000]
G4String GetProcessName() const
TClonesArray * Process
std::map< const StepID, unsigned int * > G4StatsMap
#define OBSERVES(type)
G4int GetParticlePDGID() const
TClonesArray * Region
T * make(const Args &...args) const
make new ROOT object
Definition: TFileService.h:64
step
Definition: StallMonitor.cc:83
#define UPDATE(type)
edm::Service< TFileService > fs