MdGeometryFitter.cc
Go to the documentation of this file.
1 
6 #include "MdGeometryFitter.h"
7 
8 #include <fwk/CentralConfig.h>
9 #include <fwk/RunController.h>
10 #include <fwk/LocalCoordinateSystem.h>
11 
12 #include <mdet/MDetector.h>
13 #include <mdet/MTimeVariance.h>
14 
15 #include <evt/ShowerRecData.h>
16 #include <evt/ShowerSRecData.h>
17 
18 #include <sevt/SEvent.h>
19 #include <sevt/EventTrigger.h>
20 #include <mevt/Counter.h>
21 
22 using namespace utl;
23 using namespace std;
24 
25 #define OUT(x) if ((x) <= fInfoLevel) cerr
26 
27 namespace MdGeometryFitterAG {
28 
29  template<typename G>
30  inline
31  string
32  ToString(const G& g, const CoordinateSystemPtr cs)
33  {
34  ostringstream os;
35  os << '('
36  << g.GetX(cs)/meter << ", "
37  << g.GetY(cs)/meter << ", "
38  << g.GetZ(cs)/meter << ") [m]";
39  return os.str();
40  }
41 
42 
43  // perpendicular distance from the axis
44  inline
45  double
46  RPerp(const TVector3& axis, const TVector3& station)
47  {
48  const double scal = axis.Dot(station);
49  double r2 = station.Dot(station) - scal*scal;
50 
51  return sqrt(r2);
52  }
53 
54 
57  {
59 
60  const Branch topB = cc->GetTopBranch("MdGeometryFitter");
61 
62  topB.GetChild("infoLevel").GetData(fInfoLevel);
63  if (fInfoLevel < eNone || fInfoLevel > eMinuit) {
64  INFO("<infoLevel> out of bounds");
65  return eFailure;
66  }
67  fMinuitOutput = (fInfoLevel >= eMinuit) ? true : false;
68 
69  topB.GetChild("minNumberOfStations").GetData(fMinNumberOfStations);
70  if (fMinNumberOfStations <= 2) {
71  INFO("<minNumberOfStations> must be > 2");
72  return eFailure;
73  }
74 
75  topB.GetChild("minNumberForFullCurvatureFit").GetData(fMinNumberForFullCurvatureFit);
76  if (fMinNumberForFullCurvatureFit <= 3) {
77  INFO("<fMinNumberForFullCurvatureFit> must be > 3");
78  return eFailure;
79  }
80 
81  topB.GetChild("CurvatureRadiusParameter1").GetData(fCurvatureRadiusParameter1);
82  topB.GetChild("CurvatureRadiusParameter2").GetData(fCurvatureRadiusParameter2);
83 
84  return eSuccess;
85  }
86 
88  MdGeometryFitter::Run(evt::Event& event)
89  {
90  INFO("MD geometrical reconstruction");
91 
92  // nothing to do if there is neither a SDEvent nor a MEvent
93  if ( !event.HasMEvent() || !event.HasSEvent() || !event.GetSEvent().HasTrigger() ) {
94  return eContinueLoop;
95  }
96 
97  // the SD reconstruction is a prerequisite for the md plane fit
98  if ( !event.HasRecShower() || !event.GetRecShower().HasSRecShower() ) {
99  return eContinueLoop;
100  }
101 
102  mevt::MEvent* mEvent = &event.GetMEvent();
103 
104  const det::Detector& detector = det::Detector::GetInstance();
105 
106  // the absolute points in time and space
107  const CoordinateSystemPtr siteCS = detector.GetSiteCoordinateSystem();
108  const utl::Point siteOrigin(0,0,0, siteCS);
109 
110  const evt::ShowerSRecData& sdRecShower = event.GetRecShower().GetSRecShower();
111  const utl::Point sdCorePosition = sdRecShower.GetCorePosition();
112  const utl::TimeStamp sdCoreTime = sdRecShower.GetCoreTime();
113  const utl::CoordinateSystemPtr localCS = fwk::LocalCoordinateSystem::Create(sdCorePosition);
114 
115  TVector3 sdAxis;
116  const double sdTheta = sdRecShower.GetAxis().GetTheta(localCS);
117  const double sdPhi = sdRecShower.GetAxis().GetPhi(localCS);
118  sdAxis.SetMagThetaPhi( 1., sdTheta, sdPhi); // taking the seed axis from the SD reconstruction
119 // std::cout << " sdAxis = (" << sdAxis.x() << ", " << sdAxis.y() << ", " << sdAxis.z() << ")" << std::endl;
120 
121  const double curvatureRadius = fCurvatureRadiusParameter1 + fCurvatureRadiusParameter2*sdTheta*sdTheta;
122 
123  // Create the geometry fitter
124  GeometryFitter geometryFitter;
125  geometryFitter.SetMinuitOutput(fMinuitOutput);
126 
127  TVector3 sdCorePositionLCS;
128  sdCorePositionLCS.SetX( sdCorePosition.GetX(localCS) );
129  sdCorePositionLCS.SetY( sdCorePosition.GetY(localCS) );
130  sdCorePositionLCS.SetZ( sdCorePosition.GetZ(localCS) );
131  geometryFitter.SetCore(sdCorePositionLCS);
132 
133  geometryFitter.SetRadius(curvatureRadius);
134 
135  SetTimeData(mEvent, sdCorePosition, sdCoreTime, sdAxis, geometryFitter);
136  int nCounters = geometryFitter.GetNDetectors();
137 
138  // not worth it
139  if (nCounters < fMinNumberOfStations) {
140  OUT(eFinal)
141  << "Not enough counters to reconstruct the geometry." << endl;
142  return eContinueLoop;
143  }
144 
145  geometryFitter.SetCoreFix(); // fix the core position
146 
147  if ( nCounters < fMinNumberForFullCurvatureFit ) {
148  geometryFitter.SetCurvatureFix(); // fix the radius of curvature
149  } else {
150  geometryFitter.SetCurvatureFree(); // release the radius of curvature
151  }
152 
153 // OUT(eObscure)
154 // << "sd core postion = " << ToString(sdCorePosition, siteCS) << " (site)\n"
155 
156 // OUT(eObscure)
157 // << "local/site zenith angle diff. = " << acos(Vector(0,0,1, localCS)*Vector(0,0,1, siteCS))/degree << " [deg]" << endl;
158 
159  // Fit geometry
160  if (geometryFitter.Fit() != EXIT_SUCCESS) {
161  OUT(eIntermediate) << "Failed geometrical reconstruction.\n";
162  return eContinueLoop;
163  }
164 
165  // Fill the event
166  FillRecShower(event, geometryFitter, sdCorePosition, sdCoreTime, sdAxis);
167 
168  FillCounter(mEvent, geometryFitter);
169 
170  OUT(eFinal)
171  << "MD geometrical reconstruction \n"
172  " selected counters = " << nCounters << "\n"
173  " axis = (" << geometryFitter.GetU() << ", " << geometryFitter.GetV() << ", " << geometryFitter.GetW() << ") (SD core)\n"
174  " theta = " << geometryFitter.GetTheta()/degree << " +/- "
175  << geometryFitter.GetThetaError()/degree << " [deg] (SD core)\n"
176  " phi = " << geometryFitter.GetPhi()/degree << " +/- "
177  << geometryFitter.GetPhiError()/degree << " [deg]\n"
178  " radius of curvature = " << geometryFitter.GetRadius() << " +/- "
179  << geometryFitter.GetRadiusError() << " [m]\n"
180  " ct0 = " << geometryFitter.GetCt0()/meter << " [m]\n"
181  " time chi2 = " << geometryFitter.GetChi2() << " / " << geometryFitter.GetNdof() << "\n"
182  " time residual = " << geometryFitter.GetMeanTimeResidual() << " +/- " << geometryFitter.GetTimeResidualSpread() << "\n"
183  " sd axis diff = " << acos( sdAxis.Dot(geometryFitter.GetAxis()) ) / degree << " [deg]" << endl << endl;
184 
185  ++fwk::RunController::GetInstance().GetRunData().GetNamedCounters()["MdGeometryFitter/Geometry"];
186 
187  return eSuccess;
188  }
189 
191  MdGeometryFitter::Finish()
192  {
193  return eSuccess;
194  }
195 
196  void
197  MdGeometryFitter::SetTimeData(const mevt::MEvent* mEvent, utl::Point sdCorePosition, utl::TimeStamp sdCoreTime, const TVector3& axis, GeometryFitter& fitter)
198  {
199 
201  const mdet::MDetector& mDetector = det::Detector::GetInstance().GetMDetector();
202  const mdet::MTimeVariance& timeVariance = mdet::MTimeVariance::GetInstance();
203 
204  fitter.RemoveDetectors(); // remove previous data
205 
206  // Fill the fitter with time data
207  for (mevt::MEvent::CounterConstIterator cIt = mEvent->CountersBegin(); cIt != mEvent->CountersEnd(); ++cIt) {
208 
209  if ( !cIt->IsCandidate() || !cIt->HasT50() || cIt->IsEmpty() ) { // skip counters without t50
210  continue;
211  }
212 
213  const int counterId = cIt->GetId();
214 
215  const Vector cPos = mDetector.GetCounter(counterId).GetPosition() - sdCorePosition;
216  const double x = cPos.GetX(localCS);
217  const double y = cPos.GetY(localCS);
218  const double z = cPos.GetZ(localCS);
219  const TVector3 pos(x, y, z);
220  const double time = (cIt->GetSignalT50() - sdCoreTime).GetInterval();
221 
222  const int nChannelsOn = cIt->GetNumberOfChannelsOn();
223  const double distance = RPerp(axis, pos); // using the SD axis to measure distances
224  const double sigma = sqrt( timeVariance.GetTimeSigma2(nChannelsOn, distance) );
225 
226  fitter.AddDetector (counterId, pos, time, sigma);
227 
228  }
229 
230  }
231 
232  void
233  MdGeometryFitter::FillRecShower(evt::Event& event, const GeometryFitter& geometryFitter,
234  utl::Point sdCorePosition, utl::TimeStamp sdCoreTime, TVector3 sdAxis) {
235 
236  if (!event.HasRecShower()) {
237  event.MakeRecShower();
238  }
239 
240  if (!event.GetRecShower().HasMRecShower()) {
241  event.GetRecShower().MakeMRecShower();
242  }
243 
244  evt::ShowerMRecData& showerMRec = event.GetRecShower().GetMRecShower();
245 
246  const utl::CoordinateSystemPtr localCS = fwk::LocalCoordinateSystem::Create(sdCorePosition);
247 
248  // Fill the axis
249  const Vector axis(geometryFitter.GetU(), geometryFitter.GetV(), geometryFitter.GetW(), localCS);
250  showerMRec.SetAxis(axis);
251 
252  showerMRec.SetThetaError( geometryFitter.GetThetaError() );
253  showerMRec.SetPhiError( geometryFitter.GetPhiError() );
254  showerMRec.SetThetaPhiCorrelation( geometryFitter.GetPhiError() );
255 
256  // Fill the core time
257  const utl::TimeStamp coreTime = sdCoreTime + TimeInterval( geometryFitter.GetCt0()/kSpeedOfLight );
258  const double coreTimeError = TimeInterval( geometryFitter.GetCt0Error()/kSpeedOfLight );
259  showerMRec.SetCoreTime(coreTime, coreTimeError);
260 
261  // Fill the radius of curvature
262  const double curvatureRadius = geometryFitter.GetRadius();
263  const double curvatureRadiusError = geometryFitter.GetRadiusError();
264  showerMRec.SetCurvature(curvatureRadius, curvatureRadiusError);
265 
266  // Fill the core position
267  const TVector3 corePosition1 = geometryFitter.GetCore();
268  const double xcore = corePosition1.x();
269  const double ycore = corePosition1.y();
270  const double zcore = corePosition1.z();
271  const utl::Point corePosition2( xcore, ycore, zcore, localCS);
272  showerMRec.SetCorePosition(corePosition2);
273 
274  // Fill the chi2
275  const double chi2 = geometryFitter.GetChi2();
276  const int angleNDOF = geometryFitter.GetNdof();
277  showerMRec.SetAngleChi2(chi2, angleNDOF);
278 
279  // Angle between the md and sd axis
280  const double mdSdAngle = acos( sdAxis.Dot(geometryFitter.GetAxis()));
281  showerMRec.SetMdSdAngle(mdSdAngle);
282 
283  // Fill the reconstruction flags
284  showerMRec.SetGeometryReconstructed(true);
285  showerMRec.SetCurvatureFixed( geometryFitter.IsCurvatureFix() );
286  showerMRec.SetCoreFixedGeo( geometryFitter.IsCoreFix() );
287 
288  // Fill the mean time residual
289  showerMRec.SetTimeResidualMean( geometryFitter.GetMeanTimeResidual() );
290  showerMRec.SetTimeResidualSpread( geometryFitter.GetTimeResidualSpread() );
291 
292  }
293 
294 
295  void
296  MdGeometryFitter::FillCounter(mevt::MEvent* mEvent, const GeometryFitter& fitter)
297  {
298 
299  for (mevt::MEvent::CounterIterator cIt = mEvent->CountersBegin(); cIt != mEvent->CountersEnd(); ++cIt) {
300 
301  if ( !cIt->IsCandidate() || !cIt->HasT50() || cIt->IsEmpty() ) { // skip counters without t50
302  continue;
303  }
304 
305  const int counterId = cIt->GetId();
306 
307  if (fitter.HasDetector(counterId)) {
308 
309  const double residual = fitter.GetTimeResidual(counterId);
310  cIt->SetTimeResidual(residual);
311 
312  const double planeFrontDelay = fitter.GetPlaneFrontDelay(counterId);
313  cIt->SetPlaneFrontDelay(planeFrontDelay);
314 
315  const double t50error = fitter.GetTimeError(counterId);
316  cIt->SetT50Error(t50error);
317 
318  } // end if
319 
320  } // end for loop
321 
322  } // end FillCounter
323 
324 } // end namespace MdGeometryFitterAG
325 
326 // Configure (x)emacs for this file ...
327 // Local Variables:
328 // mode: c++
329 // End:
void SetPhiError(double error)
InternalCounterCollection::ComponentConstIterator CounterConstIterator
Definition: MEvent.h:30
double RPerp(const Vector &axis, const Vector &station)
void SetCore(const TVector3 &core)
CounterConstIterator CountersBegin() const
Definition: MEvent.h:49
Point object.
Definition: Point.h:32
void SetCurvature(const double curvature, const double error)
double GetPhi(const CoordinateSystemPtr &coordinateSystem) const
azimuth (phi) angle in spherical and cylindrical coordinates
Definition: BasicVector.h:254
double GetTimeResidual(int detectorId) const
bool HasMEvent() const
Interface class to access to the SD Reconstruction of a Shower.
void SetCurvatureFixed(bool flag)
bool HasRecShower() const
double GetTheta(const CoordinateSystemPtr &coordinateSystem) const
zenith (theta) angle in spherical coordinates
Definition: BasicVector.h:248
bool HasDetector(int detectorId) const
void SetCoreTime(const utl::TimeStamp &coreTime, const utl::TimeInterval &coreTimeErr)
ShowerRecData & GetRecShower()
#define INFO(message)
Macro for logging informational messages.
Definition: ErrorLogger.h:161
utl::Point GetPosition() const
string ToString(const G &g, const CoordinateSystemPtr cs)
void Init()
Initialise the registry.
double GetPlaneFrontDelay(int detectorId) const
Branch GetChild(const std::string &childName) const
Get child of this Branch by child name.
Definition: Branch.cc:211
utl::CoordinateSystemPtr GetSiteCoordinateSystem() const
Get the coordinate system for the site.
Definition: Detector.h:137
Detector associated to muon detector hierarchy.
Definition: MDetector.h:32
void SetMdSdAngle(double a)
A TimeStamp holds GPS second and nanosecond for some event.
Definition: TimeStamp.h:110
boost::shared_ptr< const CoordinateTransformer > CoordinateSystemPtr
Shared pointer for coordinate systems.
void SetTimeResidualMean(const double mean)
Class representing a document branch.
Definition: Branch.h:107
void SetMinuitOutput(bool flag=true)
double GetX(const CoordinateSystemPtr &coordinateSystem) const
Definition: BasicVector.h:206
const utl::TimeStamp & GetCoreTime() const
time when shower front passes through the core point
Top of the hierarchy of the detector description interface.
Definition: Detector.h:81
void SetThetaPhiCorrelation(double corr)
constexpr double meter
Definition: AugerUnits.h:81
void SetCorePosition(const utl::Point &core)
constexpr double degree
#define OUT(x)
constexpr double g
Definition: AugerUnits.h:200
double GetTimeSigma2(const unsigned int nmuons, const double distance) const
const utl::Vector & GetAxis() const
void GetData(bool &b) const
Overloads of the GetData member template function.
Definition: Branch.cc:644
bool HasMRecShower() const
void SetThetaError(double error)
double GetY(const CoordinateSystemPtr &coordinateSystem) const
Definition: BasicVector.h:209
constexpr double kSpeedOfLight
A TimeInterval is used to represent time elapsed between two events.
Definition: TimeInterval.h:43
ResultFlag
Flag returned by module methods to the RunController.
Definition: VModule.h:60
void SetAxis(const utl::Vector &axis)
void SetGeometryReconstructed(bool flag=true)
Reconstruction of the shower geometry.
InternalCounterCollection::ComponentIterator CounterIterator
Definition: MEvent.h:31
void SetTimeResidualSpread(const double spread)
static CentralConfig * GetInstance()
Use this the first time you get an instance of central configuration.
void SetAngleChi2(const double chi2, const unsigned int ndof)
Vector object.
Definition: Vector.h:30
double GetTimeError(int detectorId) const
CounterConstIterator CountersEnd() const
Definition: MEvent.h:52
const utl::Point & GetCorePosition() const
Main configuration utility.
Definition: CentralConfig.h:51
Interface class to access to the Muon Reconstruction of a Shower.
double GetZ(const CoordinateSystemPtr &coordinateSystem) const
Definition: BasicVector.h:212
void SetCoreFixedGeo(bool flag)
const Counter & GetCounter(int id) const
Retrieve Counter by id.
Definition: MDetector.h:68
static Policy::type Create(const utl::Point &theOrigin)
Create the standard local coordinate system for a Point.
Root of the Muon event hierarchy.
Definition: MEvent.h:25
utl::Branch GetTopBranch(const std::string &id)
Get top branch for moduleConfigLink with given id (XML files)
void AddDetector(int id, TVector3 pos, double time, double sigma)
Note about vectors The TVector3 class is used here instead of the utl::Vector and utl::Point classses...

, generated on Tue Sep 26 2023.