Jpp - the software that should make you happy
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
Functions
JCompareDetector.cc File Reference

Auxiliary program to find differences between two detector files. More...

#include <string>
#include <iostream>
#include <iomanip>
#include "TROOT.h"
#include "TFile.h"
#include "TH1D.h"
#include "TH2D.h"
#include "JGeometry3D/JQuaternion3D.hh"
#include "JMath/JConstants.hh"
#include "JTools/JRange.hh"
#include "JTools/JQuantile.hh"
#include "JDetector/JDetector.hh"
#include "JDetector/JDetectorToolkit.hh"
#include "JDetector/JModuleRouter.hh"
#include "Jeep/JPrint.hh"
#include "Jeep/JParser.hh"
#include "Jeep/JMessage.hh"

Go to the source code of this file.

Functions

int main (int argc, char **argv)
 

Detailed Description

Auxiliary program to find differences between two detector files.


A ROOT output file with histograms is optionally produced.

Author
mjongen

Definition in file JCompareDetector.cc.

Function Documentation

int main ( int  argc,
char **  argv 
)

Definition at line 69 of file JCompareDetector.cc.

70 {
71  using namespace std;
72  using namespace JPP;
73 
74  string detectorFile_a;
75  string detectorFile_b;
76  string outputFile;
77  double precision;
78  int debug;
79 
80  try {
81 
82  JParser<> zap("Auxiliary program to find differences between two detector files.");
83 
84  zap['a'] = make_field(detectorFile_a);
85  zap['b'] = make_field(detectorFile_b);
86  zap['o'] = make_field(outputFile) = "";
87  zap['p'] = make_field(precision) = 0.001; // [ns,m]
88  zap['d'] = make_field(debug) = 3;
89 
90  zap(argc, argv);
91  }
92  catch(const exception &error) {
93  FATAL(error.what() << endl);
94  }
95 
96 
97  JDetector detector_a;
98  JDetector detector_b;
99 
100  try {
101  load(detectorFile_a, detector_a);
102  }
103  catch(const JException& error) {
104  FATAL(error);
105  }
106 
107  try {
108  load(detectorFile_b, detector_b);
109  }
110  catch(const JException& error) {
111  FATAL(error);
112  }
113 
114 
115  bool is_equal = true;
116 
117  const JModuleRouter module_router_a(detector_a);
118  const JModuleRouter module_router_b(detector_b);
119 
120  setFormat<JPosition3D> (JFormat_t(15, 9, std::ios::fixed | std::ios::showpos));
121 
122  // compare detector identifiers
123 
124  if (detector_a.getID() != detector_b.getID()) {
125 
126  DEBUG("* Different detector identifiers "
127  << setw(5) << detector_a.getID() << " (A) and " << endl
128  << setw(5) << detector_b.getID() << " (B)." << endl
129  << endl);
130 
131  is_equal = false;
132  }
133 
134 
135  // check whether the same modules are present in the file
136 
137  for (JDetector::iterator module = detector_a.begin(); module != detector_a.end(); ++module) {
138 
139  if (!module_router_b.hasModule(module->getID())) {
140 
141  DEBUG("* Module " << setw(10) << module->getID() << " is in A " << getLabel(*module) << " but not in B" << endl);
142 
143  is_equal = false;
144  }
145  }
146 
147  for (JDetector::iterator module = detector_b.begin(); module != detector_b.end(); ++module) {
148 
149  if (!module_router_a.hasModule(module->getID())) {
150 
151  DEBUG("* Module " << setw(10) << module->getID() << " is in B " << getLabel(*module) << " but not in A" << endl);
152 
153  is_equal = false;
154  }
155  }
156  DEBUG(endl);
157 
158 
159  // compare the modules that the files have in common
160 
161  DEBUG("Comparing module by module." << endl);
162 
163  for (JDetector::iterator module_a = detector_a.begin(); module_a != detector_a.end(); ++module_a) {
164 
165  if (!module_router_b.hasModule(module_a->getID())) {
166 
167  continue;
168 
169  is_equal = false;
170  }
171 
172  const JModule* module_b = &module_router_b.getModule(module_a->getID());
173 
174  DEBUG(" Module " << setw(10) << module_a->getID());
175 
176  // string and floor numbers
177 
178  if (module_a->getLocation() == module_b->getLocation()) {
179 
180  DEBUG(" " << getLabel(*module_a) << endl);
181 
182  } else {
183 
184  DEBUG(endl);
185  DEBUG(" * different location: "
186  << getLabel(*module_a) << " (A), "
187  << getLabel(*module_b) << " (B)" << endl);
188 
189  is_equal = false;
190  }
191 
192  // time offset
193 
194  if (fabs(module_a->getT0() - module_b->getT0()) > precision) {
195 
196  DEBUG(" * different T0: "
197  << module_a->getT0() << " (A), "
198  << module_b->getT0() << " (B) "
199  << ", B - A " << module_b->getT0() - module_a->getT0() << endl);
200 
201  is_equal = false;
202  }
203 
204  // quaternion calibration
205 
206  if (getAngle(module_a->getQuaternion(), module_b->getQuaternion()) > precision) {
207 
208  DEBUG(" * different quaternion calibration: "
209  << module_a->getQuaternion() << " (A), "
210  << module_b->getQuaternion() << " (B) "
211  << ", B - A " << getAngle(module_b->getQuaternion(), module_a->getQuaternion()) << endl);
212 
213  is_equal = false;
214  }
215 
216  // average DOM positions
217 
218  if (getDistance(module_a->getPosition(), module_b->getPosition()) > precision) {
219 
220  DEBUG(" * different position: "
221  << module_a->getPosition() << " (A), "
222  << module_b->getPosition() << " (B)"
223  << ", B - A " << JPosition3D(module_b->getPosition() - module_a->getPosition()) << endl);
224 
225  is_equal = false;
226  }
227 
228  // number of PMTs
229 
230  if (module_a->size() != module_b->size()) {
231 
232  DEBUG(" * different number of PMTs: "
233  << module_a->size() << " (A), "
234  << module_b->size() << " (B)" << endl);
235 
236  is_equal = false;
237  }
238 
239  // average t0
240 
241  if (!module_a->empty() &&
242  !module_b->empty()) {
243 
244  const JQuantile q = getQuantile(*module_a, *module_b);
245 
246  if (fabs(q.getMean()) > precision) {
247 
248  DEBUG(" * different average t0: "
249  << ", B - A " << q.getMean()
250  << endl);
251 
252  is_equal = false;
253  }
254  }
255 
256  // global t0
257 
258  if (fabs(module_a->getT0() - module_b->getT0()) > precision) {
259 
260  DEBUG(" * different global t0: "
261  << module_a->getT0() << " (A), "
262  << module_b->getT0() << " (B)"
263  << ", B - A " << module_b->getT0() - module_a->getT0()
264  << endl);
265 
266  is_equal = false;
267  }
268 
269  // comparing by PMT
270 
271  // t0
272 
273  for (unsigned int pmt = 0; pmt != module_a->size() && pmt != module_b->size(); ++pmt) {
274 
275  const JPMT& pmt_a = module_a->getPMT(pmt);
276  const JPMT& pmt_b = module_b->getPMT(pmt);
277 
278  if (fabs(pmt_a.getT0() - pmt_b.getT0()) > precision) {
279 
280  DEBUG(" * different T0 PMT " << pmt << ": "
281  << pmt_a.getT0() << " (A" << FILL(2,'0') << pmt << "), "
282  << pmt_b.getT0() << " (B" << FILL(2,'0') << pmt << ")"
283  << ", B - A " << pmt_b.getT0() - pmt_a.getT0()
284  << endl);
285 
286  is_equal = false;
287  }
288  }
289 
290  // positions
291 
292  for (unsigned int pmt = 0; pmt != module_a->size() && pmt != module_b->size(); ++pmt) {
293 
294  const JPMT& pmt_a = module_a->getPMT(pmt);
295  const JPMT& pmt_b = module_b->getPMT(pmt);
296 
297  // PMT positions
298 
299  if (pmt_a.getPosition().getDistance(pmt_b.getPosition()) > precision) {
300 
301  DEBUG(" * different PMT position: "
302  << pmt_a.getPosition() << " (A" << FILL(2,'0') << pmt << "), "
303  << pmt_b.getPosition() << " (B" << FILL(2,'0') << pmt << ")"
304  << ", B - A " << JPosition3D(pmt_b.getPosition() - pmt_a.getPosition()) << endl);
305 
306  is_equal = false;
307  }
308  }
309 
310  // status
311 
312  for (unsigned int pmt = 0; pmt != module_a->size() && pmt != module_b->size(); ++pmt) {
313 
314  const JPMT& pmt_a = module_a->getPMT(pmt);
315  const JPMT& pmt_b = module_b->getPMT(pmt);
316 
317  if (pmt_a.getStatus() != pmt_b.getStatus()) {
318 
319  DEBUG(" * different status PMT " << pmt << ": "
320  << pmt_a.getStatus() << " (A" << FILL(2,'0') << pmt << "), "
321  << pmt_b.getStatus() << " (B" << FILL(2,'0') << pmt << ")"
322  << endl);
323 
324  is_equal = false;
325  }
326  }
327  }
328  DEBUG(endl);
329 
330 
331  if (outputFile != "") {
332 
333  TFile out(outputFile.c_str(), "recreate");
334 
335  set<int> string;
336  set<int> floor;
337 
338  for (JDetector::iterator module = detector_a.begin(); module != detector_a.end(); ++module) {
339  string.insert(module->getString());
340  floor .insert(module->getFloor ());
341  }
342 
343  for (JDetector::iterator module = detector_b.begin(); module != detector_b.end(); ++module) {
344  string.insert(module->getString());
345  floor .insert(module->getFloor ());
346  }
347 
348 
349  TH2D M2("M2", NULL,
350  string.size(), -0.5, string.size() - 0.5,
351  floor .size(), -0.5, floor .size() - 0.5);
352 
353  for (set<int>::const_iterator i = string.begin(); i != string.end(); ++i) {
354  M2.GetXaxis()->SetBinLabel(distance(string.begin(), i) + 1, MAKE_CSTRING(*i));
355  }
356 
357  for (set<int>::const_iterator i = floor.begin(); i != floor.end(); ++i) {
358  M2.GetYaxis()->SetBinLabel(distance(floor.begin(), i) + 1, MAKE_CSTRING(*i));
359  }
360 
361  TH2D* X2 = (TH2D*) M2.Clone("X2" );
362  TH2D* Y2 = (TH2D*) M2.Clone("Y2" );
363  TH2D* Z2 = (TH2D*) M2.Clone("Z2" );
364  TH2D* T2 = (TH2D*) M2.Clone("T2" );
365  TH2D* RMS = (TH2D*) M2.Clone("RMS");
366  TH2D* R2 = (TH2D*) M2.Clone("R2" );
367  TH2D* QA = (TH2D*) M2.Clone("QA" );
368  TH2D* QB = (TH2D*) M2.Clone("QB" );
369  TH2D* QC = (TH2D*) M2.Clone("QC" );
370  TH2D* QD = (TH2D*) M2.Clone("QD" );
371  TH2D* Q2 = (TH2D*) M2.Clone("Q2" );
372 
373 
374  for (JDetector::iterator module = detector_a.begin(); module != detector_a.end(); ++module) {
375  if (!module_router_b.hasModule(module->getID()) ) {
376  M2.Fill(module->getString(), module->getFloor(), -1.0);
377  }
378  }
379 
380  for (JDetector::iterator module = detector_b.begin(); module != detector_b.end(); ++module) {
381  if (!module_router_a.hasModule(module->getID()) ) {
382  M2.Fill(module->getString(), module->getFloor(), +1.0);
383  }
384  }
385 
386  for (JDetector::iterator module_a = detector_a.begin(); module_a != detector_a.end(); ++module_a) {
387 
388  if (!module_router_b.hasModule(module_a->getID())) {
389  continue;
390  }
391 
392  const JModule* module_b = &module_router_b.getModule(module_a->getID());
393 
394  X2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), module_a->getX() - module_b->getX());
395  Y2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), module_a->getY() - module_b->getY());
396  Z2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), module_a->getZ() - module_b->getZ());
397 
398  if (module_a->getFloor() != 0 &&
399  module_b->getFloor() != 0) {
400 
401  const JQuaternion3D Q = getRotation(*module_a, *module_b);
402  const JQuantile q = getQuantile(*module_a, *module_b);
403 
405 
406  const double phi = (JVector3Z_t.getDot(q1.twist) >= 0.0 ? +1.0 : -1.0) * q1.twist.getAngle();
407 
408  R2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), phi);
409  QA ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), Q.getA());
410  QB ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), Q.getB());
411  QC ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), Q.getC());
412  QD ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), Q.getD());
413  Q2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), Q.getAngle());
414  T2 ->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), q.getMean());
415  RMS->Fill(getBin(string, module_a->getString()), getBin(floor, module_a->getFloor()), q.getSTDev());
416  }
417  }
418 
419  out.Write();
420  out.Close();
421  }
422 
423  ASSERT(is_equal);
424 
425  return 0;
426 }
Utility class to parse command line options.
Definition: JParser.hh:1500
double getAngle(const JQuaternion3D &first, const JQuaternion3D &second)
Get space angle between quanternions.
General exception.
Definition: JException.hh:23
const JStatus & getStatus() const
Get status.
Definition: JStatus.hh:68
double getB() const
Get b value.
int getFloor() const
Get floor number.
Definition: JLocation.hh:145
Data structure for a composite optical module.
Definition: JModule.hh:57
std::vector< T >::difference_type distance(typename std::vector< T >::const_iterator first, typename PhysicsEvent::const_iterator< T > second)
Specialisation of STL distance.
double getSTDev() const
Get standard deviation.
Definition: JQuantile.hh:238
Auxiliary data structure for running average, standard deviation and quantiles.
Definition: JQuantile.hh:43
std::string getLabel(const JLocation &location)
Get module label for monitoring and other applications.
Definition: JLocation.hh:246
Detector data structure.
Definition: JDetector.hh:80
Router for direct addressing of module data in detector data structure.
static JRotation getRotation
Function object to get rotation matrix to go from first to second module.
#define MAKE_CSTRING(A)
Make C-string.
Definition: JPrint.hh:151
string outputFile
double getDistance(const JVector3D &pos) const
Get distance to point.
Definition: JVector3D.hh:270
double getMean() const
Get mean value.
Definition: JQuantile.hh:224
double getDistance(const JFirst_t &first, const JSecond_t &second)
Get distance between objects.
const JQuaternion3D & getQuaternion() const
Get quaternion.
#define ASSERT(A,...)
Assert macro.
Definition: JMessage.hh:90
const JLocation & getLocation() const
Get location.
Definition: JLocation.hh:69
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
Definition: JParser.hh:1961
Data structure for PMT geometry and calibration.
Definition: JPMT.hh:47
double getY() const
Get y position.
Definition: JVector3D.hh:104
int debug
debug level
Definition: JSirene.cc:63
const JPosition3D & getPosition() const
Get position.
Definition: JPosition3D.hh:130
const JPMT & getPMT(const int index) const
Get PMT.
Definition: JModule.hh:211
Auxiliary data structure for sequence of same character.
Definition: JManip.hh:328
#define FATAL(A)
Definition: JMessage.hh:67
double getD() const
Get d value.
Data structure for unit quaternion in three dimensions.
double getAngle() const
Get rotation angle.
void load(const std::string &file_name, JDetector &detector)
Load detector from input file.
static const JVector3D JVector3Z_t(0, 0, 1)
unit z-vector
double getC() const
Get c value.
double getX() const
Get x position.
Definition: JVector3D.hh:94
double getA() const
Get a value.
double getDot(const JVector3D &vector) const
Get dot product.
Definition: JVector3D.hh:282
Data structure for position in three dimensions.
Definition: JPosition3D.hh:36
Auxiliary data structure for decomposition of quaternion in twist and swing quaternions.
Data structure for format specifications.
Definition: JManip.hh:522
double getZ() const
Get z position.
Definition: JVector3D.hh:115
#define DEBUG(A)
Message macros.
Definition: JMessage.hh:62
double getT0() const
Get time offset.