RdDirectionConvergenceChecker.cc
Go to the documentation of this file.
2 
3 #include <fwk/CentralConfig.h>
4 
5 #include <evt/Event.h>
6 #include <evt/ShowerRecData.h>
7 #include <evt/ShowerRRecData.h>
8 
9 #include <revt/REvent.h>
10 #include <revt/Header.h>
11 
12 #include <utl/ErrorLogger.h>
13 #include <utl/Reader.h>
14 #include <utl/config.h>
15 
16 
17 using namespace std;
18 using namespace fwk;
19 using namespace utl;
20 using namespace revt;
21 using namespace evt;
22 
23 
25 
26 
29  {
30  Branch topBranch =
31  CentralConfig::GetInstance()->GetTopBranch("RdDirectionConvergenceChecker");
32 
33  topBranch.GetChild("InfoLevel").GetData(fInfoLevel);
34  topBranch.GetChild("AngleEpsilon").GetData(fAngleEpsilon);
35  topBranch.GetChild("MaxIterations").GetData(fMaxIterations);
36  topBranch.GetChild("CheckMirrorZenith").GetData(fCheckMirrorZenith);
37 
38  return eSuccess;
39  }
40 
41 
43  RdDirectionConvergenceChecker::Run(evt::Event& event)
44  {
45  // nothing to do if there is no REvent
46  if (!event.HasREvent()) {
47  INFOFinal("eContinueLoop: No REvent, so no reconstruction");
48  return eContinueLoop;
49  }
50 
51  REvent& rEvent = event.GetREvent();
52  ShowerRRecData& showerrrec = event.GetRecShower().GetRRecShower();
53 
54  const int eventId = rEvent.GetHeader().GetId();
55  ostringstream info;
56 
57  // Check if we have a new event and set the iteration
58  if (!showerrrec.HasParameter(eNumberOfIterationsInDirectionFit)) {
59  info.str("");
60  info << "New event with ID: " << eventId;
61  INFODebug(info);
62 
63  // Reset the vectors
64  fAllAzimuths.clear();
65  fAllZeniths.clear();
66 
67  showerrrec.SetParameter(eNumberOfIterationsInDirectionFit, 0, false);
68  }
69 
70  // read out, increase and write back iteration counter
71  unsigned int currentIteration = showerrrec.GetParameter(eNumberOfIterationsInDirectionFit) + 1;
72  showerrrec.SetParameter(eNumberOfIterationsInDirectionFit, currentIteration, false);
73 
74  if (currentIteration == 1) {
75  /* There is no previous direction to compare against yet.
76  If we have no reconstructed radio incident direction after one iteration, we break the loop,
77  since then, the fit seems to fail allways. otherwise we just continue with the next iteration. */
78  if (!showerrrec.HasAxis()) {
79  INFO("No reconstructed shower axis was found in first iteration. Breaking the loop without axis!");
80  showerrrec.SetParameter(eFitConvergence, false);
81  return eBreakLoop;
82  }
83 
84  // Save the current angle to the vector containing all reconstructed directions.
85  fAllAzimuths.push_back(showerrrec.GetAzimuth());
86  fAllZeniths.push_back(showerrrec.GetZenith());
87 
88  return eSuccess;
89  }
90 
91  info.str("");
92  info << "Currently in " << currentIteration << " iteration for event " << eventId;
93  INFOIntermediate(info);
94 
95  // Check if the maximum number of iterations is reached
96  if (currentIteration > fMaxIterations) {
97  // if we tried mirrored zenith but did not find convergence, go back to not mirrored zenith
98  if (showerrrec.HasParameter(eMirroredZenith)) {
99  showerrrec.SetParameter(eShowerAxisX, ePreFitShowerAxisX, false);
100  showerrrec.SetParameter(eShowerAxisY, ePreFitShowerAxisY, false);
101  showerrrec.SetParameter(eShowerAxisZ, ePreFitShowerAxisZ, false);
102  showerrrec.SetParameter(eNumberOfIterationsInDirectionFit, 1, false);
103 
104  fAllAzimuths.clear();
105  fAllZeniths.clear();
106 
107  fAllAzimuths.push_back(showerrrec.GetAzimuth());
108  fAllZeniths.push_back(showerrrec.GetZenith());
109 
110  INFOFinal("Iteration with mirrowed zenith did not converge. "
111  "Restart iteration with original axis of the pre-fit");
112  return eSuccess;
113  } else {
114  INFO("Iteration limit reached without convergence! Killing Loop!");
115  showerrrec.SetParameter(eFitConvergence, false);
116  return eBreakLoop;
117  }
118  }
119 
120  // check if a previous iteration has failed
121  if (showerrrec.HasParameter(eFitSuccess) && showerrrec.GetParameter(eFitSuccess) == false) {
122  INFO("Previous fit failed, killing loop!");
123  showerrrec.SetParameter(eFitConvergence, false);
124  return eBreakLoop;
125  }
126 
127  // fit worked, get the reconstructed direction and check for convergence
128  const double curZen = showerrrec.GetZenith();
129  const double curAzi = showerrrec.GetAzimuth();
130 
131  // Calculate difference between current and previous azimuth and zenith angles
132  const double angleDiff = GetAngularDifference(curZen, curAzi, fAllZeniths.back(), fAllAzimuths.back());
133  info.str("");
134  info << "angular difference: " << angleDiff << " rad, " << angleDiff / utl::deg << " deg";
135  INFOIntermediate(info);
136 
137  if (fInfoLevel >= eInfoDebug) {
138  info.str("");
139  info << "Current iteration: " << currentIteration << ", "
140  << "last azimuth: " << fAllAzimuths.back() / deg << ", current one: " << curAzi / deg << ", "
141  << "last zenith: " << fAllZeniths.back() / deg << ", curZen one: " << curZen / deg << ", "
142  << "angular difference: " << angleDiff / deg;
143  INFODebug(info);
144  }
145 
146  // Check if the space angle difference is below the convergence limit
147  if (abs(angleDiff) <= fAngleEpsilon){
148  /* check if we would also have convergence for a down-going shower, far more probable
149  but fitting can run into minimum for a up-going zenith (especially noisy events with few stations).
150  Save information in eMirroredZenith. */
151  if (fCheckMirrorZenith && curZen / deg > 90 && !showerrrec.HasParameter(eMirroredZenith)) {
152  const auto oldZAxis = showerrrec.GetParameter(eShowerAxisZ);
153  showerrrec.SetParameter(eShowerAxisZ, -oldZAxis, false);
154  showerrrec.SetParameter(eMirroredZenith, true, true);
155  showerrrec.SetParameter(eNumberOfIterationsInDirectionFit, 1, false);
156 
157  INFOFinal("Upwarding going shower detected, restart iteration with mirrowed zenith angle");
158  return eSuccess;
159  }
160 
161  INFOFinal("Convergence reached!");
162  showerrrec.SetParameter(eFitConvergence, true);
163  return eBreakLoop;
164  }
165 
166  /* If we have more than 4 iterations, we do a check for alternating reconstructed directions.
167  if the plane fit is triggering on two different peaks, reconstructing different but alternating directions
168  in each iteration, we want to stop the process, since this is a signal for a noise dominated
169  (or otherwise unphysical) reconstruction */
170  if (fAllAzimuths.size() > 4 && fAllZeniths.size() > 4) {
171  // copy last 4 elements to new vector and reverse order
172  vector<double> latestAzi(fAllAzimuths.end() - 4, fAllAzimuths.end());
173  vector<double> latestZen(fAllZeniths.end() - 4, fAllZeniths.end());
174 
175  reverse(latestAzi.begin() , latestAzi.end());
176  reverse(latestZen.begin() , latestZen.end());
177 
178  info.str("");
179  info << "Azimuth 0 - 1: " << (latestAzi[0] - latestAzi[1]) / degree << "\n"
180  << "Azimuth 1 - 2: " << (latestAzi[1] - latestAzi[2]) / degree << "\n"
181  << "Azimuth 2 - 3: " << (latestAzi[2] - latestAzi[3]) / degree << "\n"
182  << "Zenith 0 - 1: " << (latestZen[0] - latestZen[1]) / degree << "\n"
183  << "Zenith 1 - 2: " << (latestZen[1] - latestZen[2]) / degree << "\n"
184  << "Zenith 2 - 3: " << (latestZen[2] - latestZen[3]) / degree << "\n";
185  INFODebug(info);
186 
187  const double sa1 = GetAngularDifference(latestZen[0], latestAzi[0], latestZen[1], latestAzi[1]);
188  const double sa2 = GetAngularDifference(latestZen[1], latestAzi[1], latestZen[2], latestAzi[2]);
189  const double sa3 = GetAngularDifference(latestZen[2], latestAzi[2], latestZen[3], latestAzi[3]);
190 
191  if ((abs(abs(sa1) - abs(sa2)) < 0.001*degree) && (abs(abs(sa2) - abs(sa3)) < 0.001*degree ) ) {
192  INFO("Alternation detected, breaking loop ...");
193  showerrrec.SetParameter(eFitConvergence, false);
194  return eBreakLoop;
195  }
196  }
197 
198  // Save the current angle to the vector containing all reconstructed directions.
199  // start all over again
200  fAllAzimuths.push_back(curAzi);
201  fAllZeniths.push_back(curZen);
202 
203  return eSuccess;
204  }
205 
206 
208  RdDirectionConvergenceChecker::Finish()
209  {
210  return eSuccess;
211  }
212 
213 
214  double
215  RdDirectionConvergenceChecker::GetAngularDifference(const double zen1, const double azim1,
216  const double zen2, const double azim2)
217  {
218  Vector3D curDirection;
219  Vector3D lastDirection;
220 
221  curDirection = sin(zen1)*cos(azim1), sin(zen1)*sin(azim1), cos(zen1);
222  lastDirection = sin(zen2)*cos(azim2), sin(zen2)*sin(azim2), cos(zen2);
223 
224  return Angle(curDirection, lastDirection);
225  }
226 
227 }
Branch GetTopBranch() const
Definition: Branch.cc:63
void SetParameter(Parameter i, double value, bool lock=true)
bool HasParameter(const Parameter i) const
const double degree
double Angle(const double theta1, const double phi1, const double theta2, const double phi2)
Interface class to access to the Radio part of an event.
Definition: REvent.h:42
Interface class to access to the RD Reconstruction of a Shower.
#define INFO(message)
Macro for logging informational messages.
Definition: ErrorLogger.h:161
void Init()
Initialise the registry.
Branch GetChild(const std::string &childName) const
Get child of this Branch by child name.
Definition: Branch.cc:211
bool HasREvent() const
void reverse(double arr[], int count)
constexpr double deg
Definition: AugerUnits.h:140
#define INFOIntermediate(y)
Definition: VModule.h:162
Class representing a document branch.
Definition: Branch.h:107
double GetZenith() const
returns the zenith angle (from the wave fit)
bool HasAxis() const
Return true if all 3 axis parameter are set.
double abs(const SVector< n, T > &v)
Header & GetHeader()
access to REvent Header
Definition: REvent.h:239
double GetAzimuth() const
returns the azimuth angle (from the wave fit)
void GetData(bool &b) const
Overloads of the GetData member template function.
Definition: Branch.cc:644
#define INFODebug(y)
Definition: VModule.h:163
ResultFlag
Flag returned by module methods to the RunController.
Definition: VModule.h:60
double GetParameter(const Parameter i) const
#define INFOFinal(y)
Definition: VModule.h:161
int GetId() const
Definition: REvent/Header.h:21

, generated on Tue Sep 26 2023.