ATLAS Offline Software
Loading...
Searching...
No Matches
MuonR4::FastReco::GlobalPatternFinder Class Reference

Standalone module to handle global pattern recognition. More...

#include <GlobalPatternFinder.h>

Inheritance diagram for MuonR4::FastReco::GlobalPatternFinder:
Collaboration diagram for MuonR4::FastReco::GlobalPatternFinder:

Classes

struct  Config
 Configuration object. More...
struct  HitPayload
 Hit information stored during pattern building. More...
struct  PatternState
 Pattern state object storing pattern information during construction. More...

Public Types

using StIndex = Muon::MuonStationIndex::StIndex
 Type alias for the station index.
using LayerIndex = Muon::MuonStationIndex::LayerIndex
 Type alias for the station layer index.
using SpacePointContainerVec = std::vector<const SpacePointContainer*>
 Abrivation for a vector of space-point containers.
using PatternVec = std::vector<GlobalPattern>
 Abrivation for a vector of global patterns.
using BucketPerContainer = std::unordered_map<const SpacePointContainer*, std::vector<const SpacePointBucket*>>
 Abrivation for a collection of space-point buckets grouped by their corresponding input container.
using PatternHitVisualInfo = MuonValR4::IFastRecoVisualizationTool::PatternHitVisualInfo
 Type alias for the visual information of a pattern.
using PatternHitVisualInfoVec = std::vector<PatternHitVisualInfo>
 Abrivation for a vector of visual information objects.

Public Member Functions

 GlobalPatternFinder (const std::string &name, Config &&config)
 Standard constructor.
PatternVec findPatterns (const ActsTrk::GeometryContext &gctx, const SpacePointContainerVec &spacepoints, BucketPerContainer &outBuckets) const
 Main methods steering the pattern finding.
bool msgLvl (const MSG::Level lvl) const
 Test the output level.
MsgStream & msg () const
 The standard message stream.
MsgStream & msg (const MSG::Level lvl) const
 The standard message stream.
void setLevel (MSG::Level lvl)
 Change the current logging level.

Private Types

enum class  SeedCoords : std::uint8_t { eSector , eTheta }
 Abrivation of the seed coordinates. More...
enum class  CompatibilityResult : std::int8_t { eAddHit = 0 , eBranchPattern = 1 , eRejectHit = -1 }
 : Enum for the possible outcomes of the line compatibility test of one pattern against one test hit More...
enum class  LayerOrdering : std::int8_t { eSameLayer , eLowerLayer , eHigherLayer }
 Enum to express the logical measurement layer ordering given two hits. More...
using SearchTree_t = Acts::KDTree<2, HitPayload, double, std::array, 10>
 Definition of the search tree class.
using TreeNode = std::pair<SearchTree_t::coordinate_t, HitPayload>
 Type alias for a tree node, formed by a hit payload and its indexing coordinates.
using PatternStateVec = std::vector<PatternState>

Private Member Functions

SearchTree_t constructTree (const ActsTrk::GeometryContext &gctx, const SpacePointContainerVec &spacepoints) const
 Method to construct the search tree by filling it up with spacepoints from the given containers.
PatternStateVec findPatternsInEta (const SearchTree_t &orderedSpacepoints, PatternHitVisualInfoVec *visualInfo=nullptr) const
 Method steering the building of patterns in eta.
void extendPatterns (PatternStateVec &activePatterns, const HitPayload &test, const StIndex testStation, const HitPayload &seed, const HitPayload &prevCandidate, const StIndex prevCandidateStation, PatternHitVisualInfoVec *visualInfo=nullptr) const
 Function testing pattern compatibility of a set of active patterns (patterns produced from the same seed hit) against one test hit.
std::pair< CompatibilityResult, double > checkLineCompatibility (const HitPayload &seed, const HitPayload &test, const StIndex testStation, const PatternState &pattern) const
 Method to check the line compatibility of a test hit with a given pattern.
bool isPhiCompatible (const HitPayload &test, const HitPayload &seed, const PatternState &pattern) const
 Method to check the phi compatibility of a test hit with a given pattern.
double computeLineSlope (const HitPayload &lastPatHit, const HitPayload &seed, const bool useSeed2Beamspot, const Amg::Vector3D &beamSpot) const
 Helper method to compute the line slope between the seed and the last hit in a given pattern in the R-Z plane.
double computeResidual (const HitPayload &testHit, const HitPayload &seed, const double lineSlope) const
 Method to compute the residual in globalR given the pattern line and test hit.
double computeAcceptanceWindow (const HitPayload &testHit, const HitPayload &seed, const HitPayload &lastPatHit, const double lineSlope, const bool useSeed2Beamspot, const Amg::Vector3D &beamSpot) const
 Method to compute the acceptance window in global R for a given pattern line and test hit.
PatternStateVec resolveOverlaps (PatternStateVec &&toResolve, PatternHitVisualInfoVec *visualInfo=nullptr) const
 Method to remove overlapping patterns.
GlobalPattern convertToPattern (const PatternState &candidate) const
 Method to convert a PatternState into a GlobalPattern object.
PatternVec convertToPattern (const PatternStateVec &candidates) const
 Method to convert a vector of PatternStates into GlobalPattern objects.
LayerOrdering checkLayerOrdering (const HitPayload &hit1, const HitPayload &hit2, const StIndex station1, const StIndex station2) const
 Method to check the logical layer ordering of two hits.
void addVisualInfo (const PatternState &candidate, PatternHitVisualInfo::PatternStatus status, PatternHitVisualInfoVec *visualInfo) const
 Helper function to add visual information of a given pattern (which is usually going to be destroyed) to the final container.
void initMessaging () const
 Initialize our message level and MessageSvc.

Private Attributes

SpacePointPerLayerSorter m_spSorter {}
 Spacepoint sorter per logical measurement layer.
Config m_cfg
 Global Pattern Recognition configuration.
std::string m_nm
 Message source name.
boost::thread_specific_ptr< MsgStream > m_msg_tls
 MsgStream instance (a std::cout like with print-out levels)
std::atomic< IMessageSvc * > m_imsg { nullptr }
 MessageSvc pointer.
std::atomic< MSG::Level > m_lvl { MSG::NIL }
 Current logging level.
std::atomic_flag m_initialized ATLAS_THREAD_SAFE = ATOMIC_FLAG_INIT
 Messaging initialized (initMessaging)

Detailed Description

Standalone module to handle global pattern recognition.

This tool performs global pattern recognition as the first step of the Phase-2 fast reconstruction stage. It builds global patterns of precision and non-precision hits using space-points created in upstream algorithms. It first builds patterns in eta and then adds compatible phi-only hits to the patterns. It will optionally write the final GlobalPatterns into the event store for downstream use.

Definition at line 29 of file GlobalPatternFinder.h.

Member Typedef Documentation

◆ BucketPerContainer

Abrivation for a collection of space-point buckets grouped by their corresponding input container.

Definition at line 40 of file GlobalPatternFinder.h.

◆ LayerIndex

Type alias for the station layer index.

Definition at line 34 of file GlobalPatternFinder.h.

◆ PatternHitVisualInfo

◆ PatternHitVisualInfoVec

Abrivation for a vector of visual information objects.

Definition at line 44 of file GlobalPatternFinder.h.

◆ PatternStateVec

Definition at line 199 of file GlobalPatternFinder.h.

◆ PatternVec

Abrivation for a vector of global patterns.

Definition at line 38 of file GlobalPatternFinder.h.

◆ SearchTree_t

using MuonR4::FastReco::GlobalPatternFinder::SearchTree_t = Acts::KDTree<2, HitPayload, double, std::array, 10>
private

Definition of the search tree class.

Definition at line 113 of file GlobalPatternFinder.h.

◆ SpacePointContainerVec

Abrivation for a vector of space-point containers.

Definition at line 36 of file GlobalPatternFinder.h.

◆ StIndex

Type alias for the station index.

Definition at line 32 of file GlobalPatternFinder.h.

◆ TreeNode

using MuonR4::FastReco::GlobalPatternFinder::TreeNode = std::pair<SearchTree_t::coordinate_t, HitPayload>
private

Type alias for a tree node, formed by a hit payload and its indexing coordinates.

Definition at line 115 of file GlobalPatternFinder.h.

Member Enumeration Documentation

◆ CompatibilityResult

enum class MuonR4::FastReco::GlobalPatternFinder::CompatibilityResult : std::int8_t
strongprivate

: Enum for the possible outcomes of the line compatibility test of one pattern against one test hit

Enumerator
eAddHit 

Test successfull, add the hit to the pattern.

eBranchPattern 

Test successfull with multiple pattern hits in the same logical measurement layer, branch the pattern.

eRejectHit 

Test failed, discard the hit.

Definition at line 231 of file GlobalPatternFinder.h.

231 : std::int8_t{
233 eAddHit = 0,
235 eBranchPattern = 1,
237 eRejectHit = -1,
238 };

◆ LayerOrdering

enum class MuonR4::FastReco::GlobalPatternFinder::LayerOrdering : std::int8_t
strongprivate

Enum to express the logical measurement layer ordering given two hits.

Enumerator
eSameLayer 
eLowerLayer 
eHigherLayer 

Definition at line 304 of file GlobalPatternFinder.h.

304 : std::int8_t{
305 eSameLayer,
306 eLowerLayer,
307 eHigherLayer
308 };

◆ SeedCoords

enum class MuonR4::FastReco::GlobalPatternFinder::SeedCoords : std::uint8_t
strongprivate

Abrivation of the seed coordinates.

Enumerator
eSector 

Expanded sector coordinate of the associated spectrometer sector

eTheta 

Global Theta.

Definition at line 117 of file GlobalPatternFinder.h.

117 : std::uint8_t{
119 eSector,
121 eTheta
122 };

Constructor & Destructor Documentation

◆ GlobalPatternFinder()

MuonR4::FastReco::GlobalPatternFinder::GlobalPatternFinder ( const std::string & name,
Config && config )

Standard constructor.

Parameters
nameName to be printed in the messaging
configConfiguration parameters

Definition at line 71 of file GlobalPatternFinder.cxx.

71 :
73 m_cfg{config} {
74};
AthMessaging(IMessageSvc *msgSvc, const std::string &name)
Constructor.
Config m_cfg
Global Pattern Recognition configuration.

Member Function Documentation

◆ addVisualInfo()

void MuonR4::FastReco::GlobalPatternFinder::addVisualInfo ( const PatternState & candidate,
PatternHitVisualInfo::PatternStatus status,
PatternHitVisualInfoVec * visualInfo ) const
private

Helper function to add visual information of a given pattern (which is usually going to be destroyed) to the final container.

Parameters
candidatePatternState whome visual information is to be added
statusStatus of the pattern (e.g. successfull, failed or overlap)
visualInfoFinal vector of visual information to store the visual information

Definition at line 719 of file GlobalPatternFinder.cxx.

721 {
722 if (!visualInfo) {
723 return;
724 }
725 GlobalPattern pattern {convertToPattern(cache)};
726 // Check whether the visual info about this pattern is already in the container
727 if (auto it =std::ranges::find_if(*visualInfo, [&pattern](const auto& v){
728 return v.patternCopy && *v.patternCopy == pattern; }); it != visualInfo->end()) {
729 it->status = status; // Update the status if the pattern is already in the container
730 return;
731 }
732 visualInfo->push_back(*cache.visualInfo);
733 auto& bucketVec {visualInfo->back().parentBuckets};
734 for (const auto& [_, buckets] : cache.bucketsPerContainer) {
735 bucketVec.insert(bucketVec.end(), buckets.begin(), buckets.end());
736 }
737 visualInfo->back().patternCopy = std::make_unique<GlobalPattern>(std::move(pattern));
738 visualInfo->back().status = status;
739}
GlobalPattern convertToPattern(const PatternState &candidate) const
Method to convert a PatternState into a GlobalPattern object.
status
Definition merge.py:16

◆ checkLayerOrdering()

GlobalPatternFinder::LayerOrdering MuonR4::FastReco::GlobalPatternFinder::checkLayerOrdering ( const HitPayload & hit1,
const HitPayload & hit2,
const StIndex station1,
const StIndex station2 ) const
private

Method to check the logical layer ordering of two hits.

Parameters
hit1first hit
hit2second hit
station1station index of the first hit
station2station index of the second hit
Returns
: the logical measurement layer ordering of the two hits

Hits in the same spectrometer sector

Hits in the same station and different sectors. We can have this case for hits in the overlap region of two adjacent sectors.

Hit in different stations but same station layer. Expected to happen only for Inner and Middle

If both hits are in the middle layer, the one in the barrel comes first

If both hits are in the inner layer, we use the global R, since in large sector BI comes first, while in small sector EI comes first.

If we have one hit in Inner layer for sure it comes first

If we have one hit in Outer layer for sure it comes last

If we have one hit in BarrelExtended and the other in the Middle layer, the former comes first

If we have one hit in Extended (EE) layer and the other in the Middle layer, it depends if the latter is endcap or barrel

Definition at line 576 of file GlobalPatternFinder.cxx.

579 {
580 auto getLayerOrdering = [](const bool isLayer1Lower) {
582 };
584 if (hit1.hit->msSector() == hit2.hit->msSector()) {
585 unsigned lay1 {m_spSorter.sectorLayerNum(*hit1.hit)};
586 unsigned lay2 {m_spSorter.sectorLayerNum(*hit2.hit)};
587 if (lay1 == lay2) {
589 } else {
590 return getLayerOrdering(lay1 < lay2);
591 }
592 }
594 if (station1 == station2) {
595 return getLayerOrdering(hit1.hit->msSector()->barrel() ? hit1.R < hit2.R : hit1.Z < hit2.Z);
596 }
597 LayerIndex layer1 {toLayerIndex(station1)};
598 LayerIndex layer2 {toLayerIndex(station2)};
599 if (layer1 == layer2) {
601 if (layer1 == LayerIndex::Middle) {
603 return getLayerOrdering(station1 == StIndex::BM);
604 } else if (layer1 == LayerIndex::Inner) {
606 return getLayerOrdering(hit1.R < hit2.R);
607 } else {
608 throw std::runtime_error("Unexpected to have two pattern-compatible hits one in BO and the other in EO.");
609 }
610 }
611 if (layer1 == LayerIndex::Inner || layer2 == LayerIndex::Inner) {
613 return getLayerOrdering(layer1 == LayerIndex::Inner);
614 }
615 if (layer1 == LayerIndex::Outer || layer2 == LayerIndex::Outer) {
617 return getLayerOrdering(layer2 == LayerIndex::Outer);
618 }
619 if (layer1 == LayerIndex::BarrelExtended || layer2 == LayerIndex::BarrelExtended) {
621 return getLayerOrdering(layer1 == LayerIndex::BarrelExtended);
622 }
624 if (layer1 == LayerIndex::Extended) {
625 return getLayerOrdering(station2 == StIndex::EM);
626 }
627 return getLayerOrdering(station1 == StIndex::BM);
628}
SpacePointPerLayerSorter m_spSorter
Spacepoint sorter per logical measurement layer.
Muon::MuonStationIndex::LayerIndex LayerIndex
Type alias for the station layer index.
LayerIndex toLayerIndex(ChIndex index)
convert ChIndex into LayerIndex

◆ checkLineCompatibility()

std::pair< GlobalPatternFinder::CompatibilityResult, double > MuonR4::FastReco::GlobalPatternFinder::checkLineCompatibility ( const HitPayload & seed,
const HitPayload & test,
const StIndex testStation,
const PatternState & pattern ) const
private

Method to check the line compatibility of a test hit with a given pattern.

Parameters
seedseed hit information
testtest hit information
testStationstation of the test hit
patternpattern to be extended
Returns
: a pair of the result of the test and the computed line residual for the test hit

Here we can retrieve the beamspot if desired

Helper function to get whether the test hit is within the acceptance window of the last pattern hit

Fetch the last filled station and the last inserted hit

Check the layer ordering between the last inserted hit and the test hit

Check whether the test hit is in the same layer as the last hit in the pattern

Check that the hits are not the same

We add the test hit to the pattern if they are consecutive MDT hits

If they are not consecutive MDT hits && we have no inserted hits yet (last hit = seed), we give priority to the seed and reject the test hit

If they are not consecutive MDT hits && we have inserted hits, we We draw a line using the seed and last hit being on a different layer from the second-to-last inserted hit, and we check that the test hit residual is within the acceptance window. If we have no at least 2 inserted hits yet, we compute the line using the seed and the beamspot.

Fallback when we have all the previously inserted hits on the same layer

The new hit is in a new layer. We draw a line using the last inserted hit and the seed, and we check that the test hit residual is within the acceptance window. If we have no inserted hits yet, we compute the line using the seed and the beamspot.

Definition at line 306 of file GlobalPatternFinder.cxx.

309 {
310 if (!isPhiCompatible(test, seed, pattern)) {
311 return std::make_pair(CompatibilityResult::eRejectHit, 0.);
312 }
314 const Amg::Vector3D beamSpot{Amg::Vector3D::Zero()};
315
317 auto checkResidualInWindow = [&](const HitPayload& lastPatHit,
318 const bool isUnique) {
319 // Check whether we have to use the beamspot instead of the last pattern hit to draw the line with the seed.
320 const bool useSeed2Beamspot {lastPatHit.hit == seed.hit ||
321 std::abs( lastPatHit.Z - seed.Z) <= m_cfg.minZDiff4Line ||
322 std::abs( lastPatHit.R - seed.R) <= m_cfg.minRDiff4Line};
323 const double lineSlope {computeLineSlope(lastPatHit, seed, useSeed2Beamspot, beamSpot)};
324 const double testResidual {computeResidual(test, seed, lineSlope)};
325 const double acceptanceWindow {computeAcceptanceWindow(test, seed, lastPatHit, lineSlope, useSeed2Beamspot, beamSpot)};
326 ATH_MSG_VERBOSE("Check residual in window... Residual: " << testResidual << ", Acceptance Window: " << acceptanceWindow);
327 if (pattern.visualInfo) {
328 pattern.visualInfo->hitLineInfo[test.hit] = std::make_pair(lineSlope, acceptanceWindow);
329 }
330 if (testResidual < acceptanceWindow) {
331 return std::make_pair(isUnique ? CompatibilityResult::eAddHit : CompatibilityResult::eBranchPattern, testResidual);
332 }
333 return std::make_pair(CompatibilityResult::eRejectHit, 0.);
334 };
335
337 const auto [lastHitRef, lastFilledSt] {pattern.getNthLastHit(1u)};
338 const HitPayload& lastInsertedHit {lastHitRef.get()};
339 ATH_MSG_VERBOSE("Last pat hit: " << *lastInsertedHit.hit << ", station: " << Muon::MuonStationIndex::stName(lastFilledSt));
341 const LayerOrdering orderingTest2Last {checkLayerOrdering(test, lastInsertedHit, testStation, lastFilledSt)};
342
344 if(orderingTest2Last == LayerOrdering::eSameLayer) {
346 if (test == lastInsertedHit) {
347 ATH_MSG_VERBOSE("The test hit is the same as the last inserted hit. Do not add it to the pattern.");
348 return std::make_pair(CompatibilityResult::eRejectHit, 0.);
349 }
351 if (areConsecutiveMdt(*test.hit, *lastInsertedHit.hit)) {
352 ATH_MSG_VERBOSE("The test hit is in the same layer of the last inserted one. They are consecutive MDT hits, so they are compatible.");
353 return std::make_pair(CompatibilityResult::eAddHit, 0.);
354 }
356 if (pattern.nInsertedHits == 0) {
357 ATH_MSG_VERBOSE("The test hit is in the same layer of the seed. They are not consecutive MDT hits, so they are not compatible.");
358 return std::make_pair(CompatibilityResult::eRejectHit, 0.);
359 }
363 std::size_t n {2};
364 while (n < pattern.nInsertedHits) {
365 auto [hit, st] {pattern.getNthLastHit(n)};
366 if (checkLayerOrdering(test, hit, testStation, st) != LayerOrdering::eSameLayer) {
367 return checkResidualInWindow(hit, false);
368 }
369 ++n;
370 }
372 return checkResidualInWindow(pattern.getNthLastHit(n).first, false);
373 }
376 return checkResidualInWindow(lastInsertedHit, true);
377}
#define ATH_MSG_VERBOSE(x)
bool hit(const std::valarray< int > &ids, int pdgId)
bool isPhiCompatible(const HitPayload &test, const HitPayload &seed, const PatternState &pattern) const
Method to check the phi compatibility of a test hit with a given pattern.
@ eBranchPattern
Test successfull with multiple pattern hits in the same logical measurement layer,...
@ eAddHit
Test successfull, add the hit to the pattern.
LayerOrdering checkLayerOrdering(const HitPayload &hit1, const HitPayload &hit2, const StIndex station1, const StIndex station2) const
Method to check the logical layer ordering of two hits.
double computeAcceptanceWindow(const HitPayload &testHit, const HitPayload &seed, const HitPayload &lastPatHit, const double lineSlope, const bool useSeed2Beamspot, const Amg::Vector3D &beamSpot) const
Method to compute the acceptance window in global R for a given pattern line and test hit.
LayerOrdering
Enum to express the logical measurement layer ordering given two hits.
double computeLineSlope(const HitPayload &lastPatHit, const HitPayload &seed, const bool useSeed2Beamspot, const Amg::Vector3D &beamSpot) const
Helper method to compute the line slope between the seed and the last hit in a given pattern in the R...
double computeResidual(const HitPayload &testHit, const HitPayload &seed, const double lineSlope) const
Method to compute the residual in globalR given the pattern line and test hit.
Eigen::Matrix< double, 3, 1 > Vector3D
const std::string & stName(StIndex index)
convert StIndex into a string
AthConfigFlags beamSpot(AthConfigFlags flags, str instanceName, str recoMode)
Hit information stored during pattern building.

◆ computeAcceptanceWindow()

double MuonR4::FastReco::GlobalPatternFinder::computeAcceptanceWindow ( const HitPayload & testHit,
const HitPayload & seed,
const HitPayload & lastPatHit,
const double lineSlope,
const bool useSeed2Beamspot,
const Amg::Vector3D & beamSpot ) const
private

Method to compute the acceptance window in global R for a given pattern line and test hit.

Parameters
testHittest hit information
seedseed hit information
lastPatHitlast hit in the pattern, used to compute the pattern line
lineSlopepattern line slope in the R-Z plane
useSeed2Beamspotwhether we used the beamspot instead of the last pattern hit to compute the pattern line with the seed
beamspotbeamspot global position
Returns
: the acceptance window in global R of the test hit given the pattern line

The acceptance window is defined according to the error propagation law for the residual. We have a contribution given by the geometrical amplification of the measurement error and a contribution from the uncertainty in the line slope

Reference z: last hit in the pattern or beamspot

Alpha parameter determining the propagation/ line extrapolation magnitude

Definition at line 426 of file GlobalPatternFinder.cxx.

431 {
435 const double geometricalFactor {1.+ Acts::square(lineSlope)};
437 const double& refZ {useSeed2Beamspot ? beamSpot.z() : lastPatHit.Z};
439 const double alpha {(testHit.Z-seed.Z) / (refZ - seed.Z)};
440 const double propagationFactor {1. - alpha + Acts::square(alpha)};
441 ATH_MSG_VERBOSE("Computing the acceptance window... Geometrical Factor: " << std::sqrt(geometricalFactor) << " alpha: " << alpha
442 << ", Propagation Factor: " << std::sqrt(propagationFactor) << ", Computed Window: " << m_cfg.baseRWindow * std::sqrt(geometricalFactor * propagationFactor));
443 return m_cfg.baseRWindow * std::sqrt(2*geometricalFactor * propagationFactor);
444}

◆ computeLineSlope()

double MuonR4::FastReco::GlobalPatternFinder::computeLineSlope ( const HitPayload & lastPatHit,
const HitPayload & seed,
const bool useSeed2Beamspot,
const Amg::Vector3D & beamSpot ) const
private

Helper method to compute the line slope between the seed and the last hit in a given pattern in the R-Z plane.

Parameters
lastPatHitreference to the last hit in the pattern
seedseed hit information
useSeed2Beamspotwhether we should use the beamspot instead of the last pattern hit to compute the pattern line with the seed
beamSpotbeamspot global position
Returns
: the pattern line slope in the R-Z plane

Safe-guard check: if we are inserting the first hit or if the last pattern hit and the seed are too close in Z, we use the beamspot

Definition at line 405 of file GlobalPatternFinder.cxx.

408 {
410 const double deltaR {(useSeed2Beamspot ? beamSpot.perp() - seed.R : lastPatHit.R - seed.R) };
411 const double deltaZ {(useSeed2Beamspot ? beamSpot.z() - seed.Z : lastPatHit.Z - seed.Z)};
412 ATH_MSG_VERBOSE("Computing line seed-to-lastPatHit... deltaR = " << lastPatHit.R - seed.R << ", deltaZ = " << lastPatHit.Z - seed.Z
413 << ", we use" << (useSeed2Beamspot ? " beamSpot" : " lastPatHit") << " giving " << std::format("deltaR_slope: {}, deltaZ_slope: {}", deltaR, deltaZ)
414 << ". The line slope is: " << deltaR / deltaZ);
415 return deltaR / deltaZ;
416}
double deltaR(double eta1, double eta2, double phi1, double phi2)

◆ computeResidual()

double MuonR4::FastReco::GlobalPatternFinder::computeResidual ( const HitPayload & testHit,
const HitPayload & seed,
const double lineSlope ) const
private

Method to compute the residual in globalR given the pattern line and test hit.

Parameters
testHittest hit information
seedseed hit information
lineSlopepattern line slope in the R-Z plane
Returns
: the residual in global R of the test hit with respect to the pattern line

Definition at line 418 of file GlobalPatternFinder.cxx.

420 {
421 const double signedResidual { testHit.R - seed.R - lineSlope * (testHit.Z - seed.Z)};
422 ATH_MSG_VERBOSE("Computing residual... slope: " << lineSlope << ", deltaR_residual: " << (testHit.R - seed.R) << ", deltaZ_residual: " << (testHit.Z - seed.Z) << ", signed residual: " << signedResidual);
423 return std::abs(signedResidual);
424}

◆ constructTree()

GlobalPatternFinder::SearchTree_t MuonR4::FastReco::GlobalPatternFinder::constructTree ( const ActsTrk::GeometryContext & gctx,
const SpacePointContainerVec & spacepoints ) const
private

Method to construct the search tree by filling it up with spacepoints from the given containers.

Parameters
gctxGeometry context
spacepointsVector of space point containers
Returns
: Constructed search tree

Check whether the hit belongs to the left or right sector as well

Blow-up the number of sectors by a factor of 2. The even numbers represent the segments expressed @ the sector centre. The odd numbers represent the overlap region between two adjacent sectors. For sector 16, the right overlap region is mapped to 1

Definition at line 527 of file GlobalPatternFinder.cxx.

528 {
529 SearchTree_t::vector_t rawData{};
531 for (const SpacePointContainer* spc : spacepoints) {
532 ATH_MSG_VERBOSE("Adding to the search tree "<<spc->size()<<" space point buckets");
533 for (const SpacePointBucket* bucket : *spc) {
534 ATH_MSG_VERBOSE("Processing " << bucket->size() << " spacepoint...");
535 // We can have up to 3 entries per hit (when the hit does not measure phi).
536 rawData.reserve(rawData.size() + 3*bucket->size());
537 const int sector = bucket->msSector()->sector();
538
539 for (const auto& hit : *bucket) {
540 if (hit->isStraw() && !m_cfg.useMdtHits) {
541 continue;
542 }
543 const Amg::Vector3D globalPos {bucket->msSector()->localToGlobalTransform(gctx) * hit->localPosition()};
544 // Try to duplicate the hit in the neighboring sectors if it is close to the sector border. This ensures that we can find patterns crossing the sector borders.
545 for (const auto proj : {SectorProjector::leftOverlap, SectorProjector::center, SectorProjector::rightOverlap}) {
547 const int projSector = MsTrackSeeder::ringSector(sector + Acts::toUnderlying(proj));
548 const double phi {Acts::VectorHelpers::phi(globalPos)};
549 if (hit->measuresPhi() && proj != SectorProjector::center &&
550 !sectorMap.insideSector(projSector, phi)) {
551 ATH_MSG_VERBOSE(__func__<<"() "<<__LINE__<<" Hit @"<< *hit
552 <<" is not in sector "<<projSector<<" which is "<<MsTrackSeeder::to_string(proj) <<" to "<< sector);
553 continue;
554 }
555 std::array<double, 2> coords{};
556 coords[Acts::toUnderlying(SeedCoords::eTheta)] = Acts::VectorHelpers::theta(globalPos);
557
561 coords[Acts::toUnderlying(SeedCoords::eSector)] = MsTrackSeeder::ringOverlap(2*sector + Acts::toUnderlying(proj));
562 ATH_MSG_VERBOSE(__func__<<"() "<<__LINE__<<" Add hit @"<< *hit
563 <<"\nwith global position "<<Amg::toString(globalPos) <<" and coordinates "<<coords<<" to the search tree");
564 rawData.emplace_back(std::move(coords),
565 HitPayload{hit.get(), bucket, spc, globalPos.perp(), globalPos.z(), phi});
566 }
567 }
568 }
569 }
570 ATH_MSG_VERBOSE("Create a new tree with "<<rawData.size()<<" entries. ");
571 return SearchTree_t{std::move(rawData)};
572}
Scalar phi() const
phi method
Acts::KDTree< 2, HitPayload, double, std::array, 10 > SearchTree_t
Definition of the search tree class.
@ eSector
Expanded sector coordinate of the associated spectrometer sector
static std::string to_string(const SectorProjector proj)
Print the sector projector.
static int ringSector(const int sector)
Ensure that the parsed sector number is following the MS sector schema 0 is mapped to 16 and 17 is ma...
static int ringOverlap(const int sector)
Maps the sector 33 -> 0 to close the extended MS symmetry ring.
SectorProjector
Enumeration to select the sector projection.
std::string toString(const Translation3D &translation, int precision=4)
GeoPrimitvesToStringConverter.
MsTrackSeeder::SectorProjector SectorProjector
DataVector< SpacePointBucket > SpacePointContainer
Abrivation of the space point container type.

◆ convertToPattern() [1/2]

GlobalPattern MuonR4::FastReco::GlobalPatternFinder::convertToPattern ( const PatternState & candidate) const
private

Method to convert a PatternState into a GlobalPattern object.

Parameters
candidatePatternState to be converted
Returns
: Converted GlobalPattern

Definition at line 492 of file GlobalPatternFinder.cxx.

492 {
493 GlobalPattern::HitCollection hitPerStation{};
494 for (const auto& [station, hits] : cache.hitsPerStation) {
495 auto& out = hitPerStation[station];
496 out.reserve(hits.size());
497 std::ranges::transform(hits, std::back_inserter(out), [](const HitPayload& h){ return h.hit;});
498 }
499 GlobalPattern pattern{std::move(hitPerStation)};
500 pattern.setTheta(cache.theta);
501 pattern.setPhi(cache.phi);
502 // Set the pattern sector(s) and theta.
503 const int& secCoord = cache.sectorCoord;
504 pattern.setSector((secCoord - secCoord % 2) / 2);
505 pattern.setSecondarySector((secCoord + secCoord % 2) / 2);
506 // Set pattern quality information.
507 pattern.setNPrecisionHits(cache.nPrecisionHits);
508 pattern.setNEtaNonPrecisionHits(cache.nBendingTriggerHits);
509 pattern.setNPhiHits(cache.nPhiHits);
510 pattern.setTotalResidual(cache.totalResidual);
511 return pattern;
512}
std::unordered_map< StIndex, std::vector< HitType > > HitCollection

◆ convertToPattern() [2/2]

GlobalPatternFinder::PatternVec MuonR4::FastReco::GlobalPatternFinder::convertToPattern ( const PatternStateVec & candidates) const
private

Method to convert a vector of PatternStates into GlobalPattern objects.

Parameters
candidatesPatternStates to be converted
Returns
: Vector of converted GlobalPatterns

Definition at line 515 of file GlobalPatternFinder.cxx.

515 {
517 patterns.reserve(cache.size());
518 std::transform(cache.begin(), cache.end(), std::back_inserter(patterns), [this](const PatternState& cacheEntry) {
519 GlobalPattern pattern {convertToPattern(cacheEntry)};
520 ATH_MSG_VERBOSE("Converted new pattern "<<pattern);
521 return pattern;
522 });
523 return patterns;
524}
std::vector< GlobalPattern > PatternVec
Abrivation for a vector of global patterns.
std::vector< std::string > patterns
Definition listroot.cxx:187
Pattern state object storing pattern information during construction.

◆ extendPatterns()

void MuonR4::FastReco::GlobalPatternFinder::extendPatterns ( PatternStateVec & activePatterns,
const HitPayload & test,
const StIndex testStation,
const HitPayload & seed,
const HitPayload & prevCandidate,
const StIndex prevCandidateStation,
PatternHitVisualInfoVec * visualInfo = nullptr ) const
private

Function testing pattern compatibility of a set of active patterns (patterns produced from the same seed hit) against one test hit.

At the end, activePatterns contains the surviving patterns.

Parameters
activePatternsVector of active patterns to be extended
testPairTreeNode (Hit with its tree coordinates) corresponding to the hit to be tested
testStationStation index of the hit to be tested
seedSeed hit information
prevCandidatePrevious candidate hit information
prevCandidateStationStation index of the previous candidate hit (used to check the layer ordering)
visualInfoPointer to visual information for pattern visualization (nullptr if the VisualizationTool is disabled)

Check angular compatibility of the test hit and the pattern

Add the test hit to the pattern

We branch only once, otherwise we would create duplicate patterns

Branch the pattern: we clone it and overwrite the existing hit with the test hit. Watch out, from now on lastPatHit will be the test hit

Update visual information of the original pattern

Add the new pattern to the list of next patterns

Definition at line 234 of file GlobalPatternFinder.cxx.

240 {
241 PatternStateVec nextPatterns{};
242 nextPatterns.reserve(activePatterns.size()* 2);
243
244 const unsigned refMissedLayerHits {std::ranges::min_element(activePatterns,
245 [](const auto& a, const auto& b) { return a.nMissedLayerHits < b.nMissedLayerHits; }
246 )->nMissedLayerHits};
247
248 for (PatternState& pattern : activePatterns) {
249
250 if (pattern.nMissedLayerHits >= m_cfg.maxMissedLayerHits && (!nextPatterns.empty() || pattern.nMissedLayerHits > refMissedLayerHits)) {
251 ATH_MSG_VERBOSE("Pattern " << pattern << " has already missed " << pattern.nMissedLayerHits << " hits in different layers, which is above the maximum allowed. Do not try to extend it with new hits.");
253 continue;
254 }
255
257 auto [result, residual] = checkLineCompatibility(seed, test, testStation, pattern);
258 switch (result) {
261 pattern.addHit(test, testStation, residual);
262 ATH_MSG_VERBOSE("Hit is compatible, add it to the pattern. Updated pattern: " << pattern);
263 break;
264 }
267 auto isNew = std::ranges::find_if(nextPatterns, [&test](const PatternState& p) {
268 auto [hitRef, _] = p.getNthLastHit(1u);
269 return hitRef.get() == test;
270 }) == nextPatterns.end();
271 if (!isNew) {
272 ATH_MSG_VERBOSE("Hit is compatible & in the same layer of the last added hit. The branched pattern is already in the list of next patterns. Do not add it again.");
273 continue;
274 }
276 PatternState newPattern {pattern};
277 const auto [lastHitRef, _] {pattern.getNthLastHit(1u)};
278 const HitPayload& lastPatHit {lastHitRef.get()};
279 newPattern.overWriteHit(lastPatHit, test, testStation, residual);
280 ATH_MSG_VERBOSE("Hit is compatible & in the same layer of the last added hit. Branch the pattern, new pattern: " << newPattern);
282 if (pattern.visualInfo) {
283 pattern.visualInfo->replacedHits.push_back(test.hit);
284 newPattern.visualInfo->replacedHits.push_back(lastPatHit.hit);
285 }
287 nextPatterns.push_back(std::move(newPattern));
288 break;
289 }
291 ATH_MSG_VERBOSE("Hit is not compatible with the pattern.");
292 if (pattern.visualInfo) {
293 pattern.visualInfo->discardedHits.push_back(test.hit);
294 }
295 if (checkLayerOrdering(test, prevCandidate, testStation, prevCandidateStation) != LayerOrdering::eSameLayer){
296 pattern.nMissedLayerHits++;
297 }
298 break;
299 }
300 }
301 nextPatterns.push_back(std::move(pattern));
302 }
303 std::swap(activePatterns, nextPatterns);
304};
static Double_t a
void addVisualInfo(const PatternState &candidate, PatternHitVisualInfo::PatternStatus status, PatternHitVisualInfoVec *visualInfo) const
Helper function to add visual information of a given pattern (which is usually going to be destroyed)...
std::pair< CompatibilityResult, double > checkLineCompatibility(const HitPayload &seed, const HitPayload &test, const StIndex testStation, const PatternState &pattern) const
Method to check the line compatibility of a test hit with a given pattern.
std::vector< PatternState > PatternStateVec
void swap(ElementLinkVector< DOBJ > &lhs, ElementLinkVector< DOBJ > &rhs)

◆ findPatterns()

GlobalPatternFinder::PatternVec MuonR4::FastReco::GlobalPatternFinder::findPatterns ( const ActsTrk::GeometryContext & gctx,
const SpacePointContainerVec & spacepoints,
BucketPerContainer & outBuckets ) const

Main methods steering the pattern finding.

Given the space-point containers, it creates the search tree,
builds patterns in eta, attach compatible only-phi measurements, and convert PatternStates into GlobalPatterns

Parameters
gctxGeometry context
spacepointsVector of space point containers
outBucketsoutput collection of space-point buckets grouped by their corresponding input container to be written into StoreGate.
Returns
: Vector of found patterns

Create the search tree by ordering hits in theta and expanded spectrometer sector

Find patterns in eta first

Fill the output buckets

Plot patterns

Definition at line 78 of file GlobalPatternFinder.cxx.

80 {
82 SearchTree_t orderedSpacepoints {constructTree(gctx, spacepoints)};
84 auto visualInfo {m_cfg.visionTool ? std::make_unique<PatternHitVisualInfoVec>() : nullptr};
85 PatternStateVec patterns{findPatternsInEta(orderedSpacepoints, visualInfo.get())};
86
87 // TO DO search for phi hits snd attach them to (compatible) patterns
88
90 for (const PatternState& pat : patterns) {
91 for (const auto& [spc, bucketVec] : pat.bucketsPerContainer) {
92 if (outBuckets.find(spc) == outBuckets.end()) {
93 throw std::runtime_error("The space point container associated to the pattern is not present in the output bucket map.");
94 }
95 for (const SpacePointBucket* bucket : bucketVec) {
96 outBuckets[spc].push_back(bucket);
97 }
98 }
99 }
101 if (visualInfo) {
102 m_cfg.visionTool->plotPatternBuckets(Gaudi::Hive::currentContext(), "GlobPatternFinder", std::move(*visualInfo));
103 }
105}
SearchTree_t constructTree(const ActsTrk::GeometryContext &gctx, const SpacePointContainerVec &spacepoints) const
Method to construct the search tree by filling it up with spacepoints from the given containers.
PatternStateVec findPatternsInEta(const SearchTree_t &orderedSpacepoints, PatternHitVisualInfoVec *visualInfo=nullptr) const
Method steering the building of patterns in eta.

◆ findPatternsInEta()

GlobalPatternFinder::PatternStateVec MuonR4::FastReco::GlobalPatternFinder::findPatternsInEta ( const SearchTree_t & orderedSpacepoints,
PatternHitVisualInfoVec * visualInfo = nullptr ) const
private

Method steering the building of patterns in eta.

Parameters
orderedSpacepointsSearch tree with spacepoints ordered by their corresponding coordinates
visualInfoPointer to visual information for pattern visualization (nullptr if the VisualizationTool is disabled)
Returns
: resulting vector of PatternStates successfully built

We try to build a pattern in eta starting from every hit in the three

Check the seed is in the current seeding layer, measures eta and if seeding from MDT hits is enabled

check how many existing patterns contain this hit

Define the search range.

Allowing just one value for the expanded sector range, we also include patterns extending in the overlap region of neighbouring physical sectors

Pattern search is performed within a theta window of size m_thetaSearchWindow. This window corresponds to the maximum allowed theta spread for the target pT.

Search for compatible spacepoints with the seed and check if there are enough to build a pattern

Check that the candidate hits extend at least in two layers

Sort the compatible spacepoints by global logical layer

If the two hits are in the same layer, sort them by local y coordinate.

Initialize a pattern from the seed hit

Helper function to process a new candidate hit. During pattern building, we can have pattern branching when the initial pattern is compatible with multiple hits in the same layer. These patters will be stored in activePatterns. For each new hit, extendPatterns will try to extend every active pattern and remove the ones not meeting continuation criteria.

Only-phi measurement will be treated later

Helper funtion insuring we have at the end one pattern for seed hit. If multiple survived at the end, we keep the best.

First search for compatible hits from the seed layer onwards

Then try to proceed toward the innermost layer

Check that the pattern meets the minimum requirements for trigger and precision hits

Definition at line 108 of file GlobalPatternFinder.cxx.

109 {
110 constexpr auto thetaIdx {Acts::toUnderlying(SeedCoords::eTheta)};
111 constexpr auto sectorIdx {Acts::toUnderlying(SeedCoords::eSector)};
113 using enum SeedCoords;
114 for (const auto seedingLayer : m_cfg.layerSeedings) {
115 ATH_MSG_VERBOSE("Start pattern search in eta with seeding layer "<< layerName(seedingLayer));
117 for (const auto& [seedCoords, seed] : orderedSpacepoints) {
118 const SpacePoint* seedHit {seed.hit};
120 const StIndex seedStation {m_cfg.idHelperSvc->stationIndex(seedHit->identify())};
121 const LayerIndex seedLayer {toLayerIndex(seedStation)};
122 if (seedLayer != seedingLayer || !seedHit->measuresEta() || (seedHit->isStraw() && !m_cfg.seedFromMdt)) {
123 continue;
124 }
126 auto nExistingPatterns {std::ranges::count_if(patterns, [&seed, &seedStation](const PatternState& pattern){
127 return pattern.isInPattern(seed, seedStation);
128 })};
129 if (nExistingPatterns >= m_cfg.maxSeedAttempts) {
130 ATH_MSG_DEBUG("The seed hit "<<*seedHit<<"\n coordinates "<<seedCoords<<" has already been used to build "<<nExistingPatterns<<" patterns, which is above the maximum number of attempts allowed to build a pattern from hits already used in existing patterns. Do not use it as seed for a new pattern.");
131 continue;
132 }
134 SearchTree_t::range_t selectRange{};
136 selectRange[sectorIdx].shrink(seedCoords[sectorIdx] - 0.1, seedCoords[sectorIdx] + 0.1);
138 const double thetaWindow {(seedLayer == LayerIndex::Inner || seedLayer == LayerIndex::Outer)
139 ? m_cfg.thetaSearchWindow : 0.5*m_cfg.thetaSearchWindow};
140 selectRange[thetaIdx].shrink(seedCoords[thetaIdx] - thetaWindow, seedCoords[thetaIdx] + thetaWindow);
142 auto candidateHits = orderedSpacepoints.rangeSearchWithKey(selectRange);
143 if (candidateHits.size() < m_cfg.minBendingTriggerHits + m_cfg.minBendingPrecisionHits) {
144 ATH_MSG_VERBOSE("Found "<<candidateHits.size()<<" candidate hits for seed hit "<<*seedHit<<", coordinates "<<seedCoords
145 <<". This is below the minimum number of hits required to build a pattern. Do not create a pattern.");
146 continue;
147 }
149 if (std::ranges::find_if(candidateHits, [this, seedLayer](const auto& c){
150 return m_cfg.idHelperSvc->layerIndex(c.second.hit->identify()) != seedLayer;
151 }) == candidateHits.end()) {
152 ATH_MSG_VERBOSE("All candidate hits for seed hit "<<*seedHit<<", coordinates "<<seedCoords
153 <<" are in the same layer. We need hits in at least two layers to build a pattern. Do not create a pattern.");
154 continue;
155 }
157 std::ranges::sort(candidateHits, [this](const auto& c1, const auto& c2){
158 const HitPayload& hit1 {c1.second};
159 const HitPayload& hit2 {c2.second};
160 StIndex station1 {m_cfg.idHelperSvc->stationIndex(hit1.hit->identify())};
161 StIndex station2 {m_cfg.idHelperSvc->stationIndex(hit2.hit->identify())};
162 LayerOrdering ordering {checkLayerOrdering(hit1, hit2, station1, station2)};
163 if (ordering == LayerOrdering::eSameLayer) {
165 return hit1.hit->localPosition().y() < hit2.hit->localPosition().y();
166 }
168 });
169 const auto seedItr {std::ranges::find_if(candidateHits,
170 [&seed](const auto& c){ return c.second == seed; })};
171 assert(seedItr != candidateHits.end());
173 std::vector<PatternState> activePatterns{};
174 activePatterns.emplace_back(seed, seedStation, static_cast<int>(seedCoords[sectorIdx]), seedCoords[thetaIdx]);
175 if (visualInfo) {
176 activePatterns.back().visualInfo = std::make_unique<PatternHitVisualInfo>(seedHit, seedCoords[thetaIdx] - thetaWindow, seedCoords[thetaIdx] + thetaWindow);
177 }
178
179 const HitPayload* prevCandidate {&seed};
180 StIndex prevCandidateStation {seedStation};
184 auto processNewHit = [&](const TreeNode& testPair){
185 const HitPayload& test {testPair.second};
186 const SpacePoint* testHit {testPair.second.hit};
188 if (!testHit->measuresEta()) {
189 return;
190 }
191 const StIndex testStation {m_cfg.idHelperSvc->stationIndex(testHit->identify())};
192 ATH_MSG_VERBOSE("** Check compatibility of hit "<<*testHit<<", coordinates "<<testPair.first << ". We start from " << activePatterns.size() << " active patterns.");
193 extendPatterns(activePatterns, test, testStation, seed, *prevCandidate, prevCandidateStation, visualInfo);
194 prevCandidate = &test;
195 prevCandidateStation = testStation;
196 };
198 auto ensureOnePattern = [&activePatterns, &visualInfo, this]() {
199 if (activePatterns.size() > 1) {
200 ATH_MSG_VERBOSE("Found "<<activePatterns.size()<<" patterns during the search. Remove overlaps.");
201 activePatterns = resolveOverlaps(std::move(activePatterns), visualInfo);
202 resetVisualToOverlap(visualInfo);
203 assert(activePatterns.size() == 1);
204 }
205 };
206 activePatterns.back().nInsertedHits = 0;
208 ATH_MSG_VERBOSE("Search between " << candidateHits.size() <<" candidates for compatible hits to "<<*seedHit<<", coordinates: "<<seedCoords);
209 for (auto it = std::next(seedItr); it != candidateHits.end(); ++it) {
210 processNewHit(*it);
211 }
212 ensureOnePattern();
213 activePatterns.back().nInsertedHits = 0;
215 for (auto it = std::reverse_iterator(seedItr); it != candidateHits.rend(); ++it) {
216 processNewHit(*it);
217 }
218 ensureOnePattern();
219 PatternState newPattern {std::move(activePatterns.back())};
221 if (newPattern.nBendingTriggerHits < m_cfg.minBendingTriggerHits || newPattern.nPrecisionHits < m_cfg.minBendingPrecisionHits) {
222 ATH_MSG_VERBOSE("Pattern " << newPattern << " does not meet minimum hit requirements, n bending precision/trigger hits = " << newPattern.nPrecisionHits << "/" << newPattern.nBendingTriggerHits << ". Do not create a pattern.");
224 continue;
225 }
226 newPattern.finalizePattern();
227 ATH_MSG_VERBOSE("Add new pattern "<<newPattern);
228 patterns.push_back(std::move(newPattern));
229 }
230 }
231 ATH_MSG_VERBOSE("Found in total "<<patterns.size()<<" patterns in eta before overlap removal");
232 return resolveOverlaps(std::move(patterns), visualInfo);
233}
#define ATH_MSG_DEBUG(x)
std::pair< SearchTree_t::coordinate_t, HitPayload > TreeNode
Type alias for a tree node, formed by a hit payload and its indexing coordinates.
PatternStateVec resolveOverlaps(PatternStateVec &&toResolve, PatternHitVisualInfoVec *visualInfo=nullptr) const
Method to remove overlapping patterns.
void extendPatterns(PatternStateVec &activePatterns, const HitPayload &test, const StIndex testStation, const HitPayload &seed, const HitPayload &prevCandidate, const StIndex prevCandidateStation, PatternHitVisualInfoVec *visualInfo=nullptr) const
Function testing pattern compatibility of a set of active patterns (patterns produced from the same s...
Muon::MuonStationIndex::StIndex StIndex
Type alias for the station index.
SeedCoords
Abrivation of the seed coordinates.
const std::string & layerName(LayerIndex index)
convert LayerIndex into a string
void finalizePattern()
Finalize the pattern and update its state.

◆ initMessaging()

void AthMessaging::initMessaging ( ) const
privateinherited

Initialize our message level and MessageSvc.

This method should only be called once.

Definition at line 39 of file AthMessaging.cxx.

40{
42 // If user did not set an explicit level, set a default
43 if (m_lvl == MSG::NIL) {
44 m_lvl = m_imsg ?
45 static_cast<MSG::Level>( m_imsg.load()->outputLevel(m_nm) ) :
46 MSG::INFO;
47 }
48}
std::string m_nm
Message source name.
std::atomic< IMessageSvc * > m_imsg
MessageSvc pointer.
std::atomic< MSG::Level > m_lvl
Current logging level.
IMessageSvc * getMessageSvc(bool quiet=false)

◆ isPhiCompatible()

bool MuonR4::FastReco::GlobalPatternFinder::isPhiCompatible ( const HitPayload & test,
const HitPayload & seed,
const PatternState & pattern ) const
private

Method to check the phi compatibility of a test hit with a given pattern.

Parameters
seedseed hit information
testtest hit information
patternpattern to be extended
Returns
: true if the test hit is phi compatible with the pattern, false otherwise

If the test hits does not measure phi but the pattern has already a phi, we check that the pattern is within the test hit sector.

If the test hit measures phi we check that it's compatible with the pattern phi, if avalilable, which is the average of the phi values of accepted hits of the pattern. If the pattern doesn't have a defined phi yet, we check that the test hit is in the same sector as the seed hit

Definition at line 378 of file GlobalPatternFinder.cxx.

380 {
381 const SpacePoint* testHit {test.hit};
382 const SpacePoint* seedHit {seed.hit};
384 if (!testHit->measuresPhi()) {
385 if (pattern.nPhiHits && !sectorMap.insideSector(testHit->msSector()->sector(), pattern.phi)) {
386 ATH_MSG_VERBOSE("The pattern with phi = "<<inDegrees(pattern.phi)<<" is not inside the sector of the test hit: "<<testHit->msSector()->sector());
387 return false;
388 }
391 } else {
392 if (pattern.nPhiHits) {
393 if (std::abs(CxxUtils::deltaPhi(pattern.phi, test.phi)) > m_cfg.phiTolerance) {
394 ATH_MSG_VERBOSE("The pattern with phi = "<<inDegrees(pattern.phi)<<" is not compatible with the test hit with phi "<<inDegrees(test.phi));
395 return false;
396 }
397 } else if (!sectorMap.insideSector(seedHit->msSector()->sector(), test.phi)) {
398 ATH_MSG_VERBOSE("The test hit with phi = "<<inDegrees(test.phi)<<" is not inside the sector of the seed hit: "<<seedHit->msSector()->sector());
399 return false;
400 }
401 }
402 return true;
403}
T deltaPhi(T phiA, T phiB)
Return difference phiA - phiB in range [-pi, pi].
Definition phihelper.h:42

◆ msg() [1/2]

MsgStream & AthMessaging::msg ( ) const
inlineinherited

The standard message stream.

Returns a reference to the default message stream May not be invoked before sysInitialize() has been invoked.

Definition at line 167 of file AthMessaging.h.

168{
169 MsgStream* ms = m_msg_tls.get();
170 if (!ms) {
171 if (!m_initialized.test_and_set()) initMessaging();
172 ms = new MsgStream(m_imsg,m_nm);
173 m_msg_tls.reset( ms );
174 }
175
176 ms->setLevel (m_lvl);
177 return *ms;
178}
boost::thread_specific_ptr< MsgStream > m_msg_tls
MsgStream instance (a std::cout like with print-out levels)
void initMessaging() const
Initialize our message level and MessageSvc.

◆ msg() [2/2]

MsgStream & AthMessaging::msg ( const MSG::Level lvl) const
inlineinherited

The standard message stream.

Returns a reference to the default message stream May not be invoked before sysInitialize() has been invoked.

Definition at line 182 of file AthMessaging.h.

183{ return msg() << lvl; }
MsgStream & msg() const
The standard message stream.

◆ msgLvl()

bool AthMessaging::msgLvl ( const MSG::Level lvl) const
inlineinherited

Test the output level.

Parameters
lvlThe message level to test against
Returns
boolean Indicating if messages at given level will be printed
Return values
trueMessages at level "lvl" will be printed

Definition at line 151 of file AthMessaging.h.

152{
153 // If user did not set explicit message level we have to initialize
154 // the messaging and retrieve the default via the MessageSvc.
155 if (m_lvl==MSG::NIL && !m_initialized.test_and_set()) initMessaging();
156
157 if (m_lvl <= lvl) {
158 msg() << lvl;
159 return true;
160 } else {
161 return false;
162 }
163}

◆ resolveOverlaps()

GlobalPatternFinder::PatternStateVec MuonR4::FastReco::GlobalPatternFinder::resolveOverlaps ( PatternStateVec && toResolve,
PatternHitVisualInfoVec * visualInfo = nullptr ) const
private

Method to remove overlapping patterns.

Parameters
toResolvepattern to be resolved
visualInfoPointer to visual information for pattern visualization (nullptr if the VisualizationTool is disabled)
Returns
: resolved patterns

Check if two patterns overlap in space

Determine if one pattern is better than another

Definition at line 447 of file GlobalPatternFinder.cxx.

448 {
449 PatternStateVec outputPatterns{};
450 outputPatterns.reserve(toResolve.size());
452 auto areOverlapping = [this](const PatternState& a, const PatternState& b) {
453 const bool isSectorOverlap {a.sectorCoord == b.sectorCoord ||
454 (std::abs(a.sectorCoord - b.sectorCoord) == 1 && std::abs(a.phi - b.phi) <= m_cfg.phiTolerance)};
455 return isSectorOverlap && std::abs(a.theta - b.theta) <= m_cfg.thetaSearchWindow;
456 };
458 auto isBetter = [](const PatternState& a, const PatternState& b) {
459 if (a.nBendingTriggerHits != b.nBendingTriggerHits) {
460 return a.nBendingTriggerHits > b.nBendingTriggerHits;
461 }
462 if (a.nPrecisionHits != b.nPrecisionHits) {
463 return a.nPrecisionHits > b.nPrecisionHits;
464 }
465 return a.totalResidual < b.totalResidual;
466 };
467 for (auto it = toResolve.begin(); it != toResolve.end(); ++it) {
468 if (it->isOverlap) {
470 continue;
471 }
472 for (auto jt = std::next(it); jt != toResolve.end(); ++jt) {
473 if (jt->isOverlap || !areOverlapping(*it, *jt)) {
474 continue;
475 }
476 if (isBetter(*it, *jt)) {
477 jt->isOverlap = true;
478 } else {
479 it->isOverlap = true;
480 break;
481 }
482 }
485 if (!it->isOverlap) {
486 outputPatterns.push_back( std::move(*it));
487 }
488 }
489 ATH_MSG_VERBOSE("Patterns surviving overlap removal: "<< outputPatterns.size());
490 return outputPatterns;
491}

◆ setLevel()

void AthMessaging::setLevel ( MSG::Level lvl)
inherited

Change the current logging level.

Use this rather than msg().setLevel() for proper operation with MT.

Definition at line 28 of file AthMessaging.cxx.

29{
30 m_lvl = lvl;
31}

Member Data Documentation

◆ ATLAS_THREAD_SAFE

std::atomic_flag m_initialized AthMessaging::ATLAS_THREAD_SAFE = ATOMIC_FLAG_INIT
mutableprivateinherited

Messaging initialized (initMessaging)

Definition at line 141 of file AthMessaging.h.

◆ m_cfg

Config MuonR4::FastReco::GlobalPatternFinder::m_cfg
private

Global Pattern Recognition configuration.

Definition at line 330 of file GlobalPatternFinder.h.

◆ m_imsg

std::atomic<IMessageSvc*> AthMessaging::m_imsg { nullptr }
mutableprivateinherited

MessageSvc pointer.

Definition at line 135 of file AthMessaging.h.

135{ nullptr };

◆ m_lvl

std::atomic<MSG::Level> AthMessaging::m_lvl { MSG::NIL }
mutableprivateinherited

Current logging level.

Definition at line 138 of file AthMessaging.h.

138{ MSG::NIL };

◆ m_msg_tls

boost::thread_specific_ptr<MsgStream> AthMessaging::m_msg_tls
mutableprivateinherited

MsgStream instance (a std::cout like with print-out levels)

Definition at line 132 of file AthMessaging.h.

◆ m_nm

std::string AthMessaging::m_nm
privateinherited

Message source name.

Definition at line 129 of file AthMessaging.h.

◆ m_spSorter

SpacePointPerLayerSorter MuonR4::FastReco::GlobalPatternFinder::m_spSorter {}
private

Spacepoint sorter per logical measurement layer.

Definition at line 328 of file GlobalPatternFinder.h.

328{};

The documentation for this class was generated from the following files: