ATLAS Offline Software
MuonHoughTransformer_rz.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2023 CERN for the benefit of the ATLAS collaboration
3 */
4 
6 
7 MuonHoughTransformer_rz::MuonHoughTransformer_rz(int nbins, int nbins_angle, double detectorsize, double detectorsize_angle,
8  double threshold_histo, int number_of_sectors) :
9  MuonHoughTransformer("MuonHoughTransformer_rz", nbins, nbins_angle, detectorsize, detectorsize_angle, threshold_histo, number_of_sectors),
10  m_use_residu_grad(false) {
11  m_add_weight_radius = false;
13  m_add_weight_angle = false;
14 }
15 
16 void MuonHoughTransformer_rz::fillHit(const std::shared_ptr<MuonHoughHit>& hit, double weight) {
17  const double hitz = hit->getHitz();
18 
19  if (m_ip_setting) // niels and peter alg, butterfly to be added, and to be looked into the method
20  {
21  const int sectorhit = sector(hit);
22  const double perp = hit->getRadius();
23  const double radius = hit->getAbs();
24 
25  double dotprod = 0;
27  for (double rz0 = histo->getXmin() + m_stepsize / 2.; rz0 < histo->getXmax(); rz0 += m_stepsize) {
28  if (std::abs(rz0) > radius) continue;
29 
30  double height = std::sqrt(radius * radius - rz0 * rz0);
31  double theta = std::atan2(perp, hitz) + std::atan2(rz0, height);
32  double theta_in_grad = (theta / M_PI) * 180.;
33 
34  dotprod = perp * std::sin(theta) + hitz * std::cos(theta);
35 
36  if (theta_in_grad > 180.) continue; // to keep the angle physical
37  if (theta_in_grad < 0.) continue; // idem
38 
39  if (dotprod >= 0) { fillHisto(rz0, theta_in_grad, weight, sectorhit); }
40  }
41  } else {
42  int sectorhit = 0;
43  const double radius = hit->getRadius();
44 
46  double theta_in_rad = M_PI * theta / 180.;
47  double rz0 = hitz * std::sin(theta_in_rad) - radius * std::cos(theta_in_rad);
48  double dotprod = 0;
49 
50  dotprod = radius * std::sin(theta_in_rad) + hitz * std::cos(theta_in_rad);
51  if (dotprod >= 0) { fillHisto(rz0, theta, weight, sectorhit); } // dotprod
52  }
53  } // m_atlas_setting
54 }
55 
56 int MuonHoughTransformer_rz::fillHisto(double rz0, double theta_in_grad, double weight, int sector) {
58 
59  double binwidthx = histo->getBinWidthX();
60  double binwidthy = histo->getBinWidthY();
61 
62  int filled_binnumber = histo->fill(rz0, theta_in_grad, weight);
63  // butterfly:
64 
65  // nearby sectors:
66  if (m_number_of_sectors >= 3) {
67  double third_weight = weight / 3.;
68  if (sector != 0 && sector != m_number_of_sectors - 1) {
69  m_histos.getHisto(sector + 1)->fill(rz0, theta_in_grad, third_weight);
70  m_histos.getHisto(sector - 1)->fill(rz0, theta_in_grad, third_weight);
71  } else if (sector == 0) {
72  m_histos.getHisto(sector + 1)->fill(rz0, theta_in_grad, third_weight);
73  m_histos.getHisto(m_number_of_sectors - 1)->fill(rz0, theta_in_grad, third_weight);
74  } else {
75  m_histos.getHisto(sector - 1)->fill(rz0, theta_in_grad, third_weight);
76  m_histos.getHisto(0)->fill(rz0, theta_in_grad, third_weight);
77  }
78  }
79 
80  double half_weight = 0.5 * weight;
81 
82  if (theta_in_grad - binwidthy < 0) {
83  histo->fill(rz0 + binwidthx, theta_in_grad + binwidthy, half_weight);
84  if (m_use_negative_weights) { histo->fill(rz0 - binwidthx, theta_in_grad + binwidthy, -half_weight); }
85 
86  } else if (theta_in_grad + binwidthy > 180.) {
87  histo->fill(rz0 - binwidthx, theta_in_grad - binwidthy, half_weight);
88  if (m_use_negative_weights) { histo->fill(rz0 + binwidthx, theta_in_grad - binwidthy, -half_weight); }
89  } else {
90  histo->fill(rz0 + binwidthx, theta_in_grad + binwidthy, half_weight);
91  histo->fill(rz0 - binwidthx, theta_in_grad - binwidthy, half_weight);
93  histo->fill(rz0 - binwidthx, theta_in_grad + binwidthy, -half_weight);
94  histo->fill(rz0 + binwidthx, theta_in_grad - binwidthy, -half_weight);
95  }
96  }
97  return filled_binnumber;
98 }
99 
100 double MuonHoughTransformer_rz::calculateAngle(double hitx, double hity, double hitz, double z0) {
101  // z0 is cartesian coordinate where track goes through z axis
102 
103  // analog to xyz:
104  double theta = 0;
105  double r = std::sqrt(hitx * hitx + hity * hity);
106 
107  theta = std::atan2(r, hitz - z0);
108 
109  return theta;
110 }
111 
113  std::pair<double, double> coordsmaximum, double maximum_residu_mm,
114  double maximum_residu_angle, int maxsector) const {
115 
116  std::unique_ptr<MuonHoughPattern> houghpattern = std::make_unique<MuonHoughPattern>(MuonHough::hough_rz);
117 
118  double theta{0.}, residu_distance{0.}, maximum_residu{0.};
119  double eradius{0.}, etheta{0.}, sin_theta{0.}, cos_theta{0.}, sin_phi{0.}, cos_phi{0.}, phi{0.}, ephi{0.};
120  double coordsmaximumsecondinrad = m_muonhoughmathutils.angleFromGradToRadial(coordsmaximum.second);
121  double rz0 = coordsmaximum.first;
122 
123  ATH_MSG_VERBOSE("MuonHoughTransformer_rz::hookAssociateHitsToMaximum() -- sector: " << maxsector
124  << "coordsmaximumfirst: " << rz0 << "coordsmaximumsecond: " << coordsmaximum.second
125  << " coordsmaximumsecondinrad: " << coordsmaximumsecondinrad
126  <<" size of event: " << event.size());
127 
128  for (unsigned int i = 0; i < event.size(); i++) {
129  double dotprod = 0;
130  double hitx = event.getHitx(i);
131  double hity = event.getHity(i);
132  int sectorhit = sector(event.getHit(i));
133  int maxsecmax = maxsector + 1;
134  int maxsecmin = maxsector - 1;
135  if (maxsecmin < 0) maxsecmin = m_number_of_sectors - 1;
136  if (maxsecmax > m_number_of_sectors - 1) maxsecmax = 0;
137  // select which hits could be in maximum:
138  if (sectorhit == maxsector || sectorhit == maxsecmin || sectorhit == maxsecmax) {
139  double hitz = event.getHitz(i);
140  double radius = std::hypot(hitx, hity);
141 
142  dotprod = radius * std::sin(coordsmaximumsecondinrad) + hitz * std::cos(coordsmaximumsecondinrad);
143 
144  if (dotprod >= 0) {
145  double residu_distance_mm = MuonHoughMathUtils::signedDistanceToLine(hitz, radius, rz0, coordsmaximumsecondinrad);
146 
147  // Use this code for rz scan and theta
148  //
149  double radius3 = std::hypot(hitx, hity, hitz);
150  double height{0.};
151  if (std::abs(rz0) < radius3) {
152  height = std::sqrt(radius3 * radius3 - rz0 * rz0);
153  } else {
154  height = std::sqrt(rz0 * rz0 - radius3 * radius3);
155  }
156 
157  theta = std::atan2(radius, hitz) + std::atan2(rz0, height);
158  ATH_MSG_VERBOSE("theta: " << theta << " height: " << height << " radius3: " << radius3
159  << " std::atan2(radius,hitz): " << std::atan2(radius, hitz)
160  << " +std::atan2(rz0,height): " << std::atan2(rz0, height) << " rz0: ");
161  if (m_use_residu_grad == 1) {
162  double residu_distance_grad = std::abs(std::sin(theta - coordsmaximumsecondinrad));
163  residu_distance = residu_distance_grad;
164  maximum_residu = maximum_residu_angle;
165  } else {
166  residu_distance = residu_distance_mm;
167  maximum_residu = maximum_residu_mm;
168  }
169 
170  ATH_MSG_VERBOSE("hitx: " << hitx << " hity: " << hity << " hitz: " << hitz
171  << ", residu_distance: " << residu_distance);
172  bool inmax = false;
173  if (std::abs(theta * 180. / M_PI - coordsmaximum.second) < 1.1) inmax = true;
174 
175  if (std::abs(residu_distance) < maximum_residu) // here no circular effect
176  {
177  ATH_MSG_VERBOSE(" hit added to houghpattern! -- sector number hit " << sectorhit << " max " << maxsector
178  << " detector: " << event.getHit(i)->getWhichDetector() <<
179  (inmax ? " MuonHoughTransformer_rz:: in maximum " : " OUTSIDE maximum" )<< " theta hit " << theta * 180. / M_PI << " max Hough theta "
180  << coordsmaximum.second );
181  houghpattern->addHit(event.getHit(i));
182 
183  event.getHit(i)->setAssociated(true);
184 
185  double rz0hit = residu_distance_mm + rz0;
186  eradius += rz0hit;
187  ATH_MSG_VERBOSE(__FILE__<<":"<<__LINE__<<" calculateAngle: " << theta << " calculateradius: " << rz0hit
188  << " R Z hit added to hough pattern theta hit "
189  << atan2(std::hypot(event.getHitx(i) ,event.getHity(i)), event.getHitz(i))
190  << " theta all " << coordsmaximumsecondinrad);
191  sin_theta += std::sin(theta);
192  cos_theta += std::cos(theta);
193 
194  phi = std::atan2(hity, hitx);
195 
196  sin_phi += std::sin(phi);
197  cos_phi += std::cos(phi);
198  //}
199  } else if (inmax)
200  ATH_MSG_WARNING("LOST hit in maximum distance " );
201  } // dotprod
202  } // sector constraint
203  } // hitno
204 
205  etheta = std::atan2(sin_theta, cos_theta);
206  ephi = std::atan2(sin_phi, cos_phi);
207  houghpattern->setEPhi(ephi);
208 
209  eradius = eradius / (houghpattern->size() + 0.0001);
210 
211  ATH_MSG_VERBOSE("Etheta : " << etheta << " Size houghpattern " << houghpattern->size() << " ephi "
212  << ephi );
213  houghpattern->setETheta(etheta);
214  houghpattern->setERTheta(eradius);
215  houghpattern->setECurvature(1.);
216 
217  if (houghpattern->empty()) {
218  ATH_MSG_VERBOSE("no hits found on pattern");
219  }
220 
221  else if (std::abs(eradius - rz0) > 500. || std::sin(etheta - coordsmaximumsecondinrad) > 0.05) {
222  ATH_MSG_VERBOSE("WARNING Eradius or Etheta calc. WRONG -- rz0: " << rz0
223  << " etheta: " << coordsmaximumsecondinrad<< " eradius: " << eradius << " etheta: " << etheta );
224  houghpattern->setETheta(coordsmaximumsecondinrad); // coordsmaximumsecondinrad
225  houghpattern->setERTheta(rz0);
226  }
227 
228  return houghpattern;
229 }
230 
232  if (m_add_weight_radius) {
233  return 1. / (std::abs(r0 / (m_weight_constant_radius + 1.)));
234  } else {
235  return 1;
236  } // weight function, to give more importance to patterns close to origin
237 }
238 
239 float MuonHoughTransformer_rz::weightHoughTransform(double r0, double theta) const // theta in grad
240 {
241  if (!m_add_weight_angle) {
242  return weightHoughTransform(r0);
243  } else {
244  if (m_add_weight_radius) {
245  double theta_rad = m_muonhoughmathutils.angleFromGradToRadial(theta);
246 
247  float r_theta_weight = std::abs(std::sin(theta_rad)) / (1. + std::abs((r0 / 6000.)));
248 
249  return r_theta_weight;
250  }
251 
252  else {
253  return 1;
254  } // weight function, to give more importance to patterns close to origin
255  }
256 }
MuonHoughPattern::setETheta
void setETheta(double etheta)
set theta of pattern
Definition: MuonHoughPattern.h:125
beamspotman.r
def r
Definition: beamspotman.py:676
MuonHoughHisto2DContainer::getHisto
MuonHoughHisto2D * getHisto(int id) const
return histogram at place id
Definition: MuonHoughHisto2DContainer.h:39
MuonHoughTransformer_rz::m_use_residu_grad
const bool m_use_residu_grad
Definition: MuonHoughTransformer_rz.h:30
MuonHoughMathUtils::signedDistanceToLine
static double signedDistanceToLine(double x0, double y0, double r0, double phi)
distance from (x0,y0) to the line (r0,phi), phi in rad
Definition: MuonHoughMathUtils.cxx:31
phi
Scalar phi() const
phi method
Definition: AmgMatrixBasePlugin.h:67
MuonHoughTransformer::m_muonhoughmathutils
MuonHoughMathUtils m_muonhoughmathutils
object for use of mathematical formulas for trackmodels
Definition: MuonHoughTransformer.h:102
MuonHoughHit::getHitz
double getHitz() const
returns z position
Definition: MuonHoughHit.h:161
perp
Scalar perp() const
perp method - perpenticular length
Definition: AmgMatrixBasePlugin.h:44
MuonHoughTransformer::m_weight_constant_radius
double m_weight_constant_radius
weight constant of patterns in radius coordinate
Definition: MuonHoughTransformer.h:96
theta
Scalar theta() const
theta method
Definition: AmgMatrixBasePlugin.h:75
M_PI
#define M_PI
Definition: ActiveFraction.h:11
MuonHoughPattern::setEPhi
void setEPhi(double ephi)
set phi of pattern
Definition: MuonHoughPattern.h:123
drawFromPickle.cos
cos
Definition: drawFromPickle.py:36
MuonHoughTransformer::m_use_negative_weights
bool m_use_negative_weights
use of negative weights
Definition: MuonHoughTransformer.h:99
ATH_MSG_VERBOSE
#define ATH_MSG_VERBOSE(x)
Definition: AthMsgStreamMacros.h:28
MuonHoughTransformer::m_histos
MuonHoughHisto2DContainer m_histos
histogram container
Definition: MuonHoughTransformer.h:79
MuonHoughHitContainer::addHit
void addHit(const std::shared_ptr< MuonHoughHit > &hit)
add hit to container
Definition: MuonHoughHitContainer.cxx:8
MuonHoughTransformer_rz::fillHisto
virtual int fillHisto(double rz0, double theta, double weight, int sector) override final
fill histogram with certain coordinate
Definition: MuonHoughTransformer_rz.cxx:56
dqt_zlumi_pandas.weight
int weight
Definition: dqt_zlumi_pandas.py:189
MuonHoughTransformer_rz.h
MuonHoughTransformer::m_detectorsize_angle
const double m_detectorsize_angle
range of angle coordinate
Definition: MuonHoughTransformer.h:113
MuonHoughTransformer::m_stepsize
double m_stepsize
stepsize of transform for radius coordinate
Definition: MuonHoughTransformer.h:120
MuonHoughTransformer_rz::fillHit
virtual void fillHit(const std::shared_ptr< MuonHoughHit > &hit, double weight=1.) override final
fill histograms with hit
Definition: MuonHoughTransformer_rz.cxx:16
MuonHoughPattern::setERTheta
void setERTheta(double ertheta)
set z0 of pattern
Definition: MuonHoughPattern.h:126
MuonHoughTransformer_rz::calculateAngle
static double calculateAngle(double hitx, double hity, double hitz, double z0)
Definition: MuonHoughTransformer_rz.cxx:100
MuonHoughPattern::setECurvature
void setECurvature(double curvature)
set curvature of pattern
Definition: MuonHoughPattern.h:127
event
POOL::TEvent event(POOL::TEvent::kClassAccess)
lumiFormat.i
int i
Definition: lumiFormat.py:85
MuonHoughHitContainer::size
unsigned int size() const
returns size of hitcontainer
Definition: MuonHoughHitContainer.h:104
MuonHoughTransformer_rz::weightHoughTransform
virtual float weightHoughTransform(double r0) const override final
weight houghtransform, give more importance to houghtransforms close to origin
Definition: MuonHoughTransformer_rz.cxx:231
MuonHoughTransformer::m_stepsize_per_angle
double m_stepsize_per_angle
stepsize of transform for angle coordinate
Definition: MuonHoughTransformer.h:122
TRT_PAI_physicsConstants::r0
const double r0
electron radius{cm}
Definition: TRT_PAI_physicsConstants.h:20
MuonHoughHit::getRadius
double getRadius() const
returns radius
Definition: MuonHoughHit.h:166
MuonHoughHitContainer
Definition: MuonHoughHitContainer.h:15
TRT::Track::z0
@ z0
Definition: InnerDetector/InDetCalibEvent/TRT_CalibData/TRT_CalibData/TrackInfo.h:63
MuonHoughTransformer::m_number_of_sectors
const int m_number_of_sectors
number of histograms (1 for cosmics 16 for rz)
Definition: MuonHoughTransformer.h:128
MuonHoughHit::getAbs
double getAbs() const
returns radius
Definition: MuonHoughHit.h:167
MuonHoughTransformer_rz::MuonHoughTransformer_rz
MuonHoughTransformer_rz(int nbins, int nbins_angle, double detectorsize, double detectorsize_angle, double threshold_histo, int number_of_sectors=1)
Definition: MuonHoughTransformer_rz.cxx:7
SCT_CalibAlgs::nbins
@ nbins
Definition: SCT_CalibNumbers.h:10
ParticleGun_SamplingFraction.radius
radius
Definition: ParticleGun_SamplingFraction.py:96
MuonHoughTransformer::m_ip_setting
bool m_ip_setting
use settings for patterns originating from origin
Definition: MuonHoughTransformer.h:125
MuonHoughHitContainer::empty
bool empty() const
returns if hitcontainer is empty
Definition: MuonHoughHitContainer.h:105
ATH_MSG_WARNING
#define ATH_MSG_WARNING(x)
Definition: AthMsgStreamMacros.h:32
MuonHoughHisto2D::fill
int fill(double x, double y, double weight=1.)
fill 2d histogram with point (x,y) with weight w, return binnumber filled
Definition: MuonHoughHisto2D.h:190
MuonHoughTransformer_rz::hookAssociateHitsToMaximum
std::unique_ptr< MuonHoughPattern > hookAssociateHitsToMaximum(const MuonHoughHitContainer &event, std::pair< double, double > coordsmaximum, double residu_mm, double residu_grad, int sector) const override final
pure virtual method for derived class implementation of associateHitsToMaximum method
Definition: MuonHoughTransformer_rz.cxx:112
MuonHoughTransformer::m_add_weight_radius
bool m_add_weight_radius
use weight of patterns in radius coordinate
Definition: MuonHoughTransformer.h:94
drawFromPickle.sin
sin
Definition: drawFromPickle.py:36
MuonHoughTransformer_rz::sector
int sector(const std::shared_ptr< MuonHoughHit > &hit) const override final
returns sector for coords
Definition: MuonHoughTransformer_rz.h:33
plotBeamSpotCompare.histo
histo
Definition: plotBeamSpotCompare.py:415
MuonHoughMathUtils::angleFromGradToRadial
double angleFromGradToRadial(double angle) const
converts angle in degrees to rad
Definition: MuonHoughMathUtils.h:112
MuonHoughTransformer::m_add_weight_angle
bool m_add_weight_angle
use weight of patterns in angle coordinate
Definition: MuonHoughTransformer.h:90
MuonHoughTransformer
Abstract base class, Strategy pattern.
Definition: MuonHoughTransformer.h:21
MuonHoughHisto2D
Histogram class, similar to Root's TH2D.
Definition: MuonHoughHisto2D.h:22
MuonHough::hough_rz
@ hough_rz
Definition: MuonHoughPattern.h:14