Belle II Software development
FastInterceptFinder2DFPGA.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8#include <tracking/datcon/findlets/FastInterceptFinder2DFPGA.h>
9#include <tracking/trackFindingCDC/utilities/StringManipulation.h>
10#include <vxd/dataobjects/VxdID.h>
11#include <framework/core/ModuleParamList.h>
12#include <framework/core/ModuleParamList.templateDetails.h>
13
14using namespace Belle2;
15using namespace TrackFindingCDC;
16
20
21void FastInterceptFinder2DFPGA::exposeParameters(ModuleParamList* moduleParamList, const std::string& prefix)
22{
23 Super::exposeParameters(moduleParamList, prefix);
24
25 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "isUFinder"), m_param_isUFinder,
26 "Intercept finder for u-side or v-side?", m_param_isUFinder);
27
28 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "writeGnuplotOutput"), m_param_writeGnuplotOutput,
29 "Write gnuplot debugging output to file?", m_param_writeGnuplotOutput);
30
31 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "gnuplotHSOutputFileName"), m_param_gnuplotHSOutputFileName,
32 "Name of the gnuplot debug file.", m_param_gnuplotHSOutputFileName);
33
34 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "gnuplotHSRectOutputFileName"), m_param_gnuplotHSRectOutputFileName,
35 "Name of the gnuplot debug HS sectors file.", m_param_gnuplotHSRectOutputFileName);
36
37 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "gnuplotHSCoGOutputFileName"), m_param_gnuplotHSCoGOutputFileName,
38 "Name of the gnuplot debug cluster CoG file.", m_param_gnuplotHSCoGOutputFileName);
39
40 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "maximumRecursionLevel"), m_param_maxRecursionLevel,
41 "Maximum recursion level for the fast Hough trafo algorithm.", m_param_maxRecursionLevel);
42
43 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "nAngleSectors"), m_param_nAngleSectors,
44 "Number of angle sectors (= x-axis) dividing the Hough space.", m_param_nAngleSectors);
45
46 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "nVerticalSectors"), m_param_nVerticalSectors,
47 "Number of vertical sectors (= y-axis) dividing the Hough space.", m_param_nVerticalSectors);
48
49 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "verticalHoughSpaceSize"), m_param_verticalHoughSpaceSize,
50 "Vertical size of the Hough space. Data type: long", m_param_verticalHoughSpaceSize);
51
52 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "minimumX"), m_param_minimumX,
53 "Minimum x value of the Hough space.", m_param_minimumX);
54
55 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "maximumX"), m_param_maximumX,
56 "Maximum x value of the Hough space.", m_param_maximumX);
57
58 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "minimumHSClusterSize"), m_param_MinimumHSClusterSize,
59 "Minimum size of the Hough Space clusters.", m_param_MinimumHSClusterSize);
60
61 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "maximumHSClusterSize"), m_param_MaximumHSClusterSize,
62 "Maximum size of the Hough Space clusters.", m_param_MaximumHSClusterSize);
63
64 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "maximumHSClusterSizeX"), m_param_MaximumHSClusterSizeX,
65 "Maximum size of the Hough Space clusters in horizontal direction.", m_param_MaximumHSClusterSizeX);
66
67 moduleParamList->addParameter(TrackFindingCDC::prefixed(prefix, "maximumHSClusterSizeY"), m_param_MaximumHSClusterSizeY,
68 "Maximum size of the Hough Space clusters in vertical direction.", m_param_MaximumHSClusterSizeY);
69
70}
71
73{
75
77 B2ASSERT("The maximum number of currentRecursion in u must not be larger than 14, but it is " << m_param_maxRecursionLevel,
80 // If Hough trafo for theta, divide Hough space not linear in theta, but linear in tan(theta).
81 // This leads to smaller HS sectors in the forward and backward regions, but an even distributions of extrapolated PXD hits.
82 if (not m_param_isUFinder) {
84 }
85 for (uint i = 0; i < m_param_nAngleSectors; i++) {
86 double x = m_param_minimumX + m_unitX * (double)i;
87 double xc = x + 0.5 * m_unitX;
88 if (not m_param_isUFinder) {
89 x = atan(tan(m_param_minimumX) + m_unitX * i);
90 xc = atan(tan(m_param_minimumX) + m_unitX * ((double)i + 0.5));
91 }
92
93 m_HSXLUT[i] = x;
94 m_HSSinValuesLUT[i] = convertFloatToInt(sin(x), 3);
95 m_HSCosValuesLUT[i] = convertFloatToInt(cos(x), 3);
98 m_HSXCenterLUT[i] = xc;
99 }
103
105 for (uint i = 0; i <= m_param_nVerticalSectors; i++) {
108 }
109 B2DEBUG(29, "HS size x: " << (m_param_maximumX - m_param_minimumX) << " HS size y: " << m_param_verticalHoughSpaceSize <<
110 " unitX: " << m_unitX << " unitY: " << m_unitY);
111}
112
113void FastInterceptFinder2DFPGA::apply(const std::vector<std::pair<VxdID, std::pair<long, long>>>& hits,
114 std::vector<std::pair<double, double>>& tracks)
115{
117 m_activeSectorArray.clear();
118 m_activeSectorArray.reserve(4096);
119 m_trackCandidates.clear();
120
122 m_rectcounter = 1;
123 m_rectoutstream.open(m_param_gnuplotHSRectOutputFileName.c_str(), std::ios::trunc);
124 m_cogoutstream.open(m_param_gnuplotHSCoGOutputFileName.c_str(), std::ios::trunc);
125 gnuplotoutput(hits);
126 }
127
129
131
132 for (auto& trackCand : m_trackCandidates) {
133 tracks.emplace_back(trackCand);
134 }
135
136 B2DEBUG(29, "m_activeSectorArray.size: " << m_activeSectorArray.size() << " m_trackCandidates.size: " << m_trackCandidates.size());
137
139 m_rectoutstream.close();
140 m_cogoutstream.close();
141 }
142
143}
144
145void FastInterceptFinder2DFPGA::fastInterceptFinder2d(const std::vector<std::pair<VxdID, std::pair<long, long>>>& hits,
146 uint xmin, uint xmax, uint ymin, uint ymax, uint currentRecursion)
147{
148 std::vector<std::pair<VxdID, std::pair<long, long>>> containedHits;
149
150 if (currentRecursion == m_param_maxRecursionLevel + 1) return;
151
152 // these int-divisions can cause {min, center} or {center, max} to be the same, which is a desired behaviour
153 const uint centerx = xmin + (uint)((xmax - xmin) / 2);
154 const uint centery = ymin + (uint)((ymax - ymin) / 2);
155 const uint xIndexCache[3] = {xmin, centerx, xmax};
156 const uint yIndexCache[3] = {ymin, centery, ymax};
157
158 for (int i = 0; i < 2 ; ++i) {
159 const uint left = xIndexCache[i];
160 const uint right = xIndexCache[i + 1];
161 const uint localIndexX = left;
162
163 if (left == right) continue;
164
165 const double& localLeft = m_HSXLUT[left];
166 const double& localRight = m_HSXLUT[right];
167 const short& sinLeft = m_HSSinValuesLUT[left];
168 const short& cosLeft = m_HSCosValuesLUT[left];
169 const short& sinRight = m_HSSinValuesLUT[right];
170 const short& cosRight = m_HSCosValuesLUT[right];
171
172 // the sin and cos of the current center can't be stored in a LUT, as the number of possible centers
173 // is quite large and the logic would become rather complex
174 const short& sinCenter = m_HSCenterSinValuesLUT[(left + right) / 2];
175 const short& cosCenter = m_HSCenterCosValuesLUT[(left + right) / 2];
176
177 for (int j = 0; j < 2; ++j) {
178
179 const uint lowerIndex = yIndexCache[j];
180 const uint upperIndex = yIndexCache[j + 1];
181
182 const uint localIndexY = lowerIndex;
183 const long& localUpperCoordinate = m_HSYLUT[lowerIndex];
184 const long& localLowerCoordinate = m_HSYLUT[upperIndex];
185
186 if (lowerIndex == upperIndex) continue;
187
188 std::vector<bool> layerHits(7); /* For layer filter */
189 containedHits.clear();
190 for (auto& hit : hits) {
191 const VxdID& sensor = hit.first;
192
193 const long& m = hit.second.first;
194 const long& a = hit.second.second;
195
196 long yLeft = m * cosLeft + a * sinLeft;
197 long yRight = m * cosRight + a * sinRight;
198 long yCenter = m * cosCenter + a * sinCenter;
199 long derivativeyLeft = m * -sinLeft + a * cosLeft;
200 long derivativeyRight = m * -sinRight + a * cosRight;
201 long derivativeyCenter = m * -sinCenter + a * cosCenter;
202
203 // Only interested in the rising arm of the sinosoidal curves.
204 // Thus if derivative on both sides of the cell is negative, ignore and continue.
205 if (derivativeyLeft < 0 and derivativeyRight < 0 and derivativeyCenter < 0) continue;
206
207 /* Check if HS-parameter curve is inside (or outside) actual sub-HS */
208 if ((yLeft <= localUpperCoordinate and yRight >= localLowerCoordinate) or
209 (yCenter <= localUpperCoordinate and yLeft >= localLowerCoordinate and yRight >= localLowerCoordinate) or
210 (yCenter >= localLowerCoordinate and yLeft <= localUpperCoordinate and yRight <= localUpperCoordinate)) {
211 layerHits[sensor.getLayerNumber()] = true; /* layer filter */
212 containedHits.emplace_back(hit);
213 }
214 }
215
216 if (layerFilter(layerHits) > 0) {
217 // recursive call of fastInterceptFinder2d, until currentRecursion == m_maxRecursionLevel
218 if (currentRecursion < m_param_maxRecursionLevel) {
219
221 m_rectoutstream << "set object " << m_rectcounter << " rect from " << localLeft << ", " << localLowerCoordinate <<
222 " to " << localRight << ", " << localUpperCoordinate << " fc rgb \"" <<
223 m_const_rectColor[currentRecursion % 8] << "\" fs solid 0.5 behind" << std::endl;
225 }
226
227 fastInterceptFinder2d(containedHits, left, right, lowerIndex, upperIndex, currentRecursion + 1);
228
229 } else {
230 m_SectorArray[localIndexY * m_param_nAngleSectors + localIndexX] = -layerFilter(layerHits);
231 m_activeSectorArray.push_back(std::make_pair(localIndexX, localIndexY));
232
234 m_rectoutstream << "set object " << m_rectcounter << " rect from " << localLeft << ", " << localLowerCoordinate <<
235 " to " << localRight << ", " << localUpperCoordinate << " fc rgb \"" <<
236 m_const_rectColor[currentRecursion % 8] << "\" fs solid 0.5 behind" << std::endl;
238 }
239
240 }
241 }
242 }
243 }
244}
245
247{
248 // cell content meanings:
249 // -3, -4 : active sector, not yet visited
250 // 0 : non-active sector (will never be visited, only checked)
251 // 1,2,3...: index of the clusters
252
253 m_clusterCount = 1;
254
255 // this sorting makes sure the clusters can be searched from bottom left of the HS to top right
256 // normally, a C++ array looks like a matrix:
257 // (0 , 0) ... (maxX, 0 )
258 // ... ...
259 // (0, maxY) ... (maxX, maxY)
260 // but for sorting we want it to be like regular coordinates
261 // (0, maxY) ... (maxX, maxY)
262 // ... ...
263 // (0, 0 ) ... (maxX, 0 )
264 // By setting the offset to the maximum allowed number of cells (2^14) and simplifying
265 // (16384 - a.second) * 16384 + a.first < (16384 - b.second) * 16384 + b.first
266 // we get the formula below
267 auto sortSectors = [](const std::pair<uint, uint> a, const std::pair<uint, uint> b) {
268 return ((int)b.second - (int)a.second) * 16384 < (int)b.first - (int)a.first;
269 };
270 std::sort(m_activeSectorArray.begin(), m_activeSectorArray.end(), sortSectors);
271
272 for (const auto& currentCell : m_activeSectorArray) {
273 const uint currentIndex = currentCell.second * m_param_nAngleSectors + currentCell.first;
274 if (m_SectorArray[currentIndex] > -1) continue;
275
276 m_clusterInitialPosition = currentCell;
277 m_clusterCoG = currentCell;
278 m_clusterSize = 1;
279 m_SectorArray[currentIndex] = m_clusterCount;
280 // Check for HS sectors connected to each other which could form a cluster
281 DepthFirstSearch(currentCell.first, currentCell.second);
282 // if cluster valid (i.e. not too small and not too big): finalize!
284 double CoGX = (((double)m_clusterCoG.first / (double)m_clusterSize) + 0.5) * m_unitX + m_param_minimumX;
285 if (not m_param_isUFinder) {
286 CoGX = atan(tan(m_param_minimumX) + m_unitX * (((double)m_clusterCoG.first / (double)m_clusterSize) + 0.5));
287 }
288 double CoGY = m_param_verticalHoughSpaceSize - ((double)m_clusterCoG.second / (double)m_clusterSize - 0.5) * m_unitY;
289
290 if (m_param_isUFinder) {
291 // Angle from Hough space only yields phi-pi/2, so adjust for this and make sure phi still is in -pi...+pi
292 double trackPhi = CoGX + M_PI_2;
293 if (trackPhi < -M_PI) trackPhi += 2 * M_PI;
294 if (trackPhi > M_PI) trackPhi -= 2 * M_PI;
295
296 // 1./CoGY * 1e10 yields trackRadius in mm. To convert to µm, which all other values are in,
297 // multiplication by another 1e3 is required -> total of 1e13
298 double trackRadius = 1. / CoGY * 1e+13;
299
300 m_trackCandidates.emplace_back(std::make_pair(trackPhi, trackRadius));
301 } else {
302 m_trackCandidates.emplace_back(std::make_pair(CoGX, CoGY));
303 }
304 B2DEBUG(29, "m_clusterCoG.first: " << m_clusterCoG.first << " " << ((double)m_clusterCoG.first / (double)m_clusterSize) <<
305 " m_clusterCoG.second: " << m_clusterCoG.second << " " << ((double)m_clusterCoG.second / (double)m_clusterSize) <<
306 " CoGX: " << CoGX << " CoGY: " << CoGY);
307
309 m_cogoutstream << CoGX << " " << CoGY << std::endl;
310 }
311 }
313 }
314}
315
316void FastInterceptFinder2DFPGA::DepthFirstSearch(uint lastIndexX, uint lastIndexY)
317{
319
320 for (uint currentIndexY = lastIndexY; currentIndexY >= lastIndexY - 1; currentIndexY--) {
321 if (abs((int)m_clusterInitialPosition.second - (int)currentIndexY) >= m_param_MaximumHSClusterSizeY or
323 for (uint currentIndexX = lastIndexX; currentIndexX <= lastIndexX + 1; currentIndexX++) {
324 if (abs((int)m_clusterInitialPosition.first - (int)currentIndexX) >= m_param_MaximumHSClusterSizeX or
326
327 // The cell (currentIndexX, currentIndexY) is the current one has already been checked, so continue
328 if (lastIndexX == currentIndexX && lastIndexY == currentIndexY) continue;
329
330 // first check bounds to avoid out-of-bound array access
331 // as they are uints, they are always >= 0, and in case of an overflow they would be too large
332 if (currentIndexX < m_param_nAngleSectors and currentIndexY < m_param_nVerticalSectors) {
333
334 if (m_SectorArray[currentIndexY * m_param_nAngleSectors + currentIndexX] < 0 /*and m_clusterSize < m_MaximumHSClusterSize*/) {
335 // Only continue searching if the current cluster is smaller than the maximum cluster size
336 m_SectorArray[currentIndexY * m_param_nAngleSectors + currentIndexX] = m_clusterCount;
337 m_clusterCoG = std::make_pair(m_clusterCoG.first + currentIndexX, m_clusterCoG.second + currentIndexY);
339 // search in the next Hough Space cells...
340 DepthFirstSearch(currentIndexX, currentIndexY);
341 }
342
343 }
344 }
345 }
346}
347
348void FastInterceptFinder2DFPGA::gnuplotoutput(const std::vector<std::pair<VxdID, std::pair<long, long>>>& hits)
349{
350 std::ofstream hsoutstream;
351 hsoutstream.open(m_param_gnuplotHSOutputFileName.c_str(), std::ios::trunc);
352
353 hsoutstream << "set pointsize 1.5\nset style line 42 lc rgb '#0060ad' pt 7 # circle" << std::endl;
354
355 hsoutstream << "set style line 80 lt rgb \"#808080\"" << std::endl;
356 hsoutstream << "set style line 81 lt 0" << std::endl;
357 hsoutstream << "set style line 81 lt rgb \"#808080\"" << std::endl << std::endl;
358
359 hsoutstream << "set style line 1 lt rgb \"#A00000\" lw 1 pt 1" << std::endl;
360 hsoutstream << "set style line 2 lt rgb \"#00A000\" lw 1 pt 6" << std::endl;
361 hsoutstream << "set style line 3 lt rgb \"#000000\" lw 1 pt 6" << std::endl;
362
363 hsoutstream << "set style line 3 lt rgb 'black' lw 1 pt 6" << std::endl;
364 hsoutstream << "set style line 4 lt rgb 'blue' lw 1 pt 6" << std::endl;
365 hsoutstream << "set style line 5 lt rgb 'green' lw 1 pt 6" << std::endl;
366 hsoutstream << "set style line 6 lt rgb 'red' lw 1 pt 6" << std::endl;
367
368 hsoutstream << "# Description position\nset key top right" << std::endl << std::endl;
369 hsoutstream << "# Grid and border style\nset grid back linestyle 81\nset border 3 back linestyle 80" << std::endl << std::endl;
370
371 hsoutstream << "# No mirrors\nset xtics nomirror\nset ytics nomirror" << std::endl << std::endl;
372 hsoutstream << "# Encoding\nset encoding utf8" << std::endl << std::endl;
373 hsoutstream << "set xlabel \"x\"\nset ylabel \"y\"" << std::endl << std::endl;
374
375 hsoutstream << "set xrange [-pi-0.5:pi+0.5]" << std::endl << std::endl;
376
377 hsoutstream << "load '" << m_param_gnuplotHSRectOutputFileName << "'" << std::endl << std::endl;
378
379 uint count = 0;
380 for (auto& hit : hits) {
381 const VxdID& id = hit.first;
382 int layer = id.getLayerNumber();
383 // Multiplication with 1000 is necessary, as in the actual intercept finding step, cos and sin are multiplied by 1000, too.
384 // To directly compare the information in the gnuplot HoughSpace, just multiply by 1000 here instead of adding another
385 // '1000 * ' when writing to the gnuplot debug file.
386 const long xc = 1000 * hit.second.first;
387 const long yc = 1000 * hit.second.second;
388
389 // only plot when derivative is positive
390 hsoutstream << "plot " << xc << " * -sin(x) + " << yc << " * cos(x) > 0 ? " << xc << " * cos(x) + " << yc <<
391 " * sin(x) : 1/0 notitle linestyle " << layer << " # " << id << std::endl;
392 if (count < hits.size() - 1) hsoutstream << "re";
393 count++;
394 }
395
396 hsoutstream << std::endl;
397 hsoutstream << "replot '" << m_param_gnuplotHSCoGOutputFileName << "' u 1:2 w p ls 42 notitle" << std::endl << std::endl;
398 hsoutstream << "pause -1" << std::endl;
399 hsoutstream.close();
400}
std::vector< int > m_SectorArray
vector containing only the 1D representation of active cells to speed up processing
uint m_param_MinimumHSClusterSize
minimum cluster size of sectors belonging to intercepts in the Hough Space
void gnuplotoutput(const std::vector< std::pair< VxdID, std::pair< long, long > > > &hits)
gnuplot output for debugging
const std::string m_const_rectColor[8]
color definition for the sector debug output
void FindHoughSpaceCluster()
Find Hough Space clusters.
double m_param_maximumX
maximum x value of the Hough Space, defaults to the value for u-side
uint m_clusterSize
size of the current cluster
void fastInterceptFinder2d(const std::vector< std::pair< VxdID, std::pair< long, long > > > &hits, uint xmin, uint xmax, uint ymin, uint ymax, uint currentRecursion)
find intercepts in the 2D Hough Space by recursively calling itself until no hits are assigned to a g...
void initialize() override
Create the store arrays.
std::array< long, 16385 > m_HSYLUT
y values of the Hough Space sector boarders
std::array< double, 16385 > m_HSXLUT
x values of the Hough Space sector boarders
std::vector< std::pair< double, double > > m_trackCandidates
vector containing track candidates, consisting of the found intersection values in the Hough Space
std::string m_param_gnuplotHSRectOutputFileName
gnuplot HS sector output filename
uint m_param_nVerticalSectors
number of sectors of the Hough Space on the vertical axis
bool m_param_isUFinder
Is this the intercept finder for the u-side hits (r-phi) or v-side (r-z)?
long m_param_verticalHoughSpaceSize
vertical size of the Hough Space, defaults to the value for u-side
std::array< long, 16385 > m_HSCosValuesLUT
cosine values of the Hough Space sector boarder coordinates
void DepthFirstSearch(uint lastIndexX, uint lastIndexY)
Perform depth first search recursive algorithm to find clusters in the Hough Space.
std::array< long, 16385 > m_HSSinValuesLUT
Look-Up-Tables for values as cache to speed up calculation sine values of the Hough Space sector boar...
std::array< long, 16384 > m_HSCenterCosValuesLUT
cosine values of the Hough Space sector center coordinates
uint m_param_maxRecursionLevel
maximum number of recursive calls of fastInterceptFinder2d
std::ofstream m_rectoutstream
HS sector debug file.
std::ofstream m_cogoutstream
HS CoG debug file.
void apply(const std::vector< std::pair< VxdID, std::pair< long, long > > > &hits, std::vector< std::pair< double, double > > &tracks) override
Load in the prepared hits and create tracks for extrapolation to PXD.
std::pair< int, int > m_clusterCoG
center of gravity containing describing the current best track parameters in the Hough Space
double m_param_minimumX
minimum x value of the Hough Space, defaults to the value for u-side
uint m_param_nAngleSectors
number of sectors of the Hough Space on the horizontal axis
std::string m_param_gnuplotHSOutputFileName
gnuplot HS output filename
std::vector< std::pair< uint, uint > > m_activeSectorArray
vector containing information for each cell whether it contained enough hits after m_maxRecursionLeve...
std::array< long, 16384 > m_HSYCenterLUT
y values of the Hough Space sector centers
uint m_param_MaximumHSClusterSizeX
maximum cluster size in x of sectors belonging to intercepts in the Hough Space
std::string m_param_gnuplotHSCoGOutputFileName
gnuplot HS sector output filename
uint m_param_MaximumHSClusterSize
maximum cluster size of sectors belonging to intercepts in the Hough Space
unsigned short layerFilter(std::vector< bool > layer)
Layer filter, checks if at least hits from 3 layers are in a set of hits.
FastInterceptFinder2DFPGA()
Find intercepts in the 2D Hough space.
uint m_rectcounter
count HS debug rectangles
void exposeParameters(ModuleParamList *moduleParamList, const std::string &prefix) override
Expose the parameters of the sub findlets.
std::array< double, 16384 > m_HSXCenterLUT
x values of the Hough Space sector centers
std::pair< int, int > m_clusterInitialPosition
start cell of the recursive cluster finding in the Hough Space
uint m_param_MaximumHSClusterSizeY
maximum cluster size in y of sectors belonging to intercepts in the Hough Space
TrackFindingCDC::Findlet< const std::pair< VxdID, std::pair< long, long > >, std::pair< double, double > > Super
Parent class.
std::array< long, 16384 > m_HSCenterSinValuesLUT
sine values of the Hough Space sector center coordinates
The Module parameter list class.
Class to uniquely identify a any structure of the PXD and SVD.
Definition VxdID.h:33
void addParameter(const std::string &name, T &paramVariable, const std::string &description, const T &defaultValue)
Adds a new parameter to the module list.
double tan(double a)
tan for double
Definition beamHelpers.h:31
double atan(double a)
atan for double
Definition beamHelpers.h:34
long convertFloatToInt(double value, int power)
Convert float or double to long int for more similarity to the FPGA implementation.
Abstract base class for different kinds of events.