LArSoft  v09_90_00
Liquid Argon Software toolkit - https://larsoft.org/
RemovalBaseTool.cc
Go to the documentation of this file.
1 
9 #include "Pandora/AlgorithmHeaders.h"
10 
12 
14 
15 using namespace pandora;
16 
17 namespace lar_content
18 {
19 
20 RemovalBaseTool::RemovalBaseTool() :
21  m_minSeparation(1.f),
22  m_distanceToLine(0.5f)
23 {
24 }
25 
26 //------------------------------------------------------------------------------------------------------------------------------------------
27 
28 bool RemovalBaseTool::PassElementChecks(const TensorType::Element &element, const HitType hitType) const
29 {
30  const Cluster *pMuonCluster(nullptr), *const pDeltaRayCluster(element.GetCluster(hitType));
31 
32  if (m_pParentAlgorithm->GetMuonCluster(element.GetOverlapResult().GetCommonMuonPfoList(), hitType, pMuonCluster) != STATUS_CODE_SUCCESS)
33  return false;
34 
35  const float separation(LArClusterHelper::GetClosestDistance(pDeltaRayCluster, pMuonCluster));
36 
37  return separation <= m_minSeparation;
38 }
39 
40 //------------------------------------------------------------------------------------------------------------------------------------------
41 
42 bool RemovalBaseTool::IsMuonEndpoint(const TensorType::Element &element, const bool ignoreHitType, const HitType hitTypeToIgnore) const
43 {
44  for (const HitType hitType : {TPC_VIEW_U, TPC_VIEW_V, TPC_VIEW_W})
45  {
46  if (ignoreHitType && (hitType == hitTypeToIgnore))
47  continue;
48 
49  const Cluster *pMuonCluster(nullptr), *const pDeltaRayCluster(element.GetCluster(hitType));
50 
51  if (m_pParentAlgorithm->GetMuonCluster(element.GetOverlapResult().GetCommonMuonPfoList(), hitType, pMuonCluster) != STATUS_CODE_SUCCESS)
52  return true;
53 
54  float xMinDR(-std::numeric_limits<float>::max()), xMaxDR(+std::numeric_limits<float>::max());
55  pDeltaRayCluster->GetClusterSpanX(xMinDR, xMaxDR);
56 
57  float xMinCR(-std::numeric_limits<float>::max()), xMaxCR(+std::numeric_limits<float>::max());
58  pMuonCluster->GetClusterSpanX(xMinCR, xMaxCR);
59 
60  if ((xMinDR < xMinCR) || (xMaxDR > xMaxCR))
61  return true;
62 
63  float zMinDR(-std::numeric_limits<float>::max()), zMaxDR(+std::numeric_limits<float>::max());
64  pDeltaRayCluster->GetClusterSpanZ(xMinDR, xMaxDR, zMinDR, zMaxDR);
65 
66  float zMinCR(-std::numeric_limits<float>::max()), zMaxCR(+std::numeric_limits<float>::max());
67  pMuonCluster->GetClusterSpanZ(xMinCR, xMaxCR, zMinCR, zMaxCR);
68 
69  if ((zMinDR < zMinCR) || (zMaxDR > zMaxCR))
70  return true;
71  }
72 
73  return false;
74 }
75 
76 //------------------------------------------------------------------------------------------------------------------------------------------
77 
78 bool RemovalBaseTool::IsBestElement(const TensorType::Element &element, const HitType hitType, const TensorType::ElementList &elementList,
79  const ClusterSet &modifiedClusters) const
80 {
81  const float chiSquared(element.GetOverlapResult().GetReducedChi2());
82  const unsigned int hitSum(element.GetClusterU()->GetNCaloHits() + element.GetClusterV()->GetNCaloHits() + element.GetClusterW()->GetNCaloHits());
83 
84  for (const TensorType::Element &testElement : elementList)
85  {
86  if (modifiedClusters.count(testElement.GetClusterU()) || modifiedClusters.count(testElement.GetClusterV()) ||
87  modifiedClusters.count(testElement.GetClusterW()))
88  continue;
89 
90  if (testElement.GetCluster(hitType) != element.GetCluster(hitType))
91  continue;
92 
93  if ((testElement.GetClusterU() == element.GetClusterU()) && (testElement.GetClusterV() == element.GetClusterV()) &&
94  (testElement.GetClusterW() == element.GetClusterW()))
95  continue;
96 
97  const unsigned int testHitSum(
98  testElement.GetClusterU()->GetNCaloHits() + testElement.GetClusterV()->GetNCaloHits() + testElement.GetClusterW()->GetNCaloHits());
99  const float testChiSquared(testElement.GetOverlapResult().GetReducedChi2());
100 
101  if ((testHitSum < hitSum) || ((testHitSum == hitSum) && (testChiSquared > chiSquared)))
102  continue;
103 
104  if (this->PassElementChecks(testElement, hitType))
105  return false;
106  }
107 
108  return true;
109 }
110 
111 //------------------------------------------------------------------------------------------------------------------------------------------
112 
114  const CartesianVector &hitPosition, const CartesianVector &lineStart, const CartesianVector &lineEnd, const float distanceToLine) const
115 {
116  CartesianVector lineDirection(lineStart - lineEnd);
117  lineDirection = lineDirection.GetUnitVector();
118 
119  const float transverseDistanceFromLine(lineDirection.GetCrossProduct(hitPosition - lineStart).GetMagnitude());
120 
121  if (transverseDistanceFromLine > distanceToLine)
122  return false;
123 
124  return true;
125 }
126 
127 //------------------------------------------------------------------------------------------------------------------------------------------
128 
129 bool RemovalBaseTool::IsInLineSegment(const CartesianVector &lowerBoundary, const CartesianVector &upperBoundary, const CartesianVector &point) const
130 {
131  const float segmentBoundaryGradient = (-1.f) * (upperBoundary.GetX() - lowerBoundary.GetX()) / (upperBoundary.GetZ() - lowerBoundary.GetZ());
132  const float xPointOnUpperLine((point.GetZ() - upperBoundary.GetZ()) / segmentBoundaryGradient + upperBoundary.GetX());
133  const float xPointOnLowerLine((point.GetZ() - lowerBoundary.GetZ()) / segmentBoundaryGradient + lowerBoundary.GetX());
134 
135  if (std::fabs(xPointOnUpperLine - point.GetX()) < std::numeric_limits<float>::epsilon())
136  return true;
137 
138  if (std::fabs(xPointOnLowerLine - point.GetX()) < std::numeric_limits<float>::epsilon())
139  return true;
140 
141  if ((point.GetX() > xPointOnUpperLine) && (point.GetX() > xPointOnLowerLine))
142  return false;
143 
144  if ((point.GetX() < xPointOnUpperLine) && (point.GetX() < xPointOnLowerLine))
145  return false;
146 
147  return true;
148 }
149 
150 //------------------------------------------------------------------------------------------------------------------------------------------
151 
152 void RemovalBaseTool::FindExtrapolatedHits(const Cluster *const pCluster, const CartesianVector &lowerBoundary,
153  const CartesianVector &upperBoundary, CaloHitList &collectedHits) const
154 {
155  CaloHitList caloHitList;
156  pCluster->GetOrderedCaloHitList().FillCaloHitList(caloHitList);
157 
158  for (const CaloHit *const pCaloHit : caloHitList)
159  {
160  if (!this->IsInLineSegment(lowerBoundary, upperBoundary, pCaloHit->GetPositionVector()))
161  continue;
162 
163  if (!this->IsCloseToLine(pCaloHit->GetPositionVector(), lowerBoundary, upperBoundary, m_distanceToLine))
164  continue;
165 
166  collectedHits.push_back(pCaloHit);
167  }
168 }
169 
170 //------------------------------------------------------------------------------------------------------------------------------------------
171 
172 StatusCode RemovalBaseTool::ProjectDeltaRayPositions(const TensorType::Element &element, const HitType hitType, CartesianPointVector &projectedPositions) const
173 {
174  HitTypeVector hitTypes({TPC_VIEW_U, TPC_VIEW_V, TPC_VIEW_W});
175 
176  hitTypes.erase(std::find(hitTypes.begin(), hitTypes.end(), hitType));
177 
178  const Cluster *const pCluster1(element.GetCluster(hitTypes[0]));
179  const Cluster *const pCluster2(element.GetCluster(hitTypes[1]));
180 
181  return m_pParentAlgorithm->GetProjectedPositions(pCluster1, pCluster2, projectedPositions);
182 }
183 
184 //------------------------------------------------------------------------------------------------------------------------------------------
185 
186 StatusCode RemovalBaseTool::ReadSettings(const TiXmlHandle xmlHandle)
187 {
188  PANDORA_RETURN_RESULT_IF_AND_IF(STATUS_CODE_SUCCESS, STATUS_CODE_NOT_FOUND, !=, XmlHelper::ReadValue(xmlHandle, "MinSeparation", m_minSeparation));
189 
190  PANDORA_RETURN_RESULT_IF_AND_IF(STATUS_CODE_SUCCESS, STATUS_CODE_NOT_FOUND, !=, XmlHelper::ReadValue(xmlHandle, "DistanceToLine", m_distanceToLine));
191 
192  return STATUS_CODE_SUCCESS;
193 }
194 
195 } // namespace lar_content
float m_minSeparation
The minimum delta ray - parent muon cluster separation required to investigate a delta/cosmic ray clu...
pandora::StatusCode GetProjectedPositions(const pandora::Cluster *const pCluster1, const pandora::Cluster *const pCluster2, pandora::CartesianPointVector &projectedPositions) const
Use two clusters from different views to calculate projected positions in the remaining third view...
Header file for the removal base tool class.
float m_distanceToLine
The maximum perpendicular distance of a position to a line for it to be considered close...
ThreeViewDeltaRayMatchingAlgorithm * m_pParentAlgorithm
Address of the parent matching algorithm.
TFile f
Definition: plotHisto.C:6
bool IsBestElement(const TensorType::Element &element, const pandora::HitType hitType, const TensorType::ElementList &elementList, const pandora::ClusterSet &modifiedClusters) const
Determine whether the input element is the best to use to modify the contaminated cluster (best is de...
bool IsInLineSegment(const pandora::CartesianVector &lowerBoundary, const pandora::CartesianVector &upperBoundary, const pandora::CartesianVector &point) const
Whether the projection of a given position lies on a defined line.
Header file for the cluster helper class.
virtual bool PassElementChecks(const TensorType::Element &element, const pandora::HitType hitType) const =0
Determine whether element satifies simple checks.
void FindExtrapolatedHits(const pandora::Cluster *const pCluster, const pandora::CartesianVector &lowerBoundary, const pandora::CartesianVector &upperBoundary, pandora::CaloHitList &collectedHits) const
Collect the hits that are closest to and can be projected onto a defined line.
bool IsCloseToLine(const pandora::CartesianVector &hitPosition, const pandora::CartesianVector &lineStart, const pandora::CartesianVector &lineEnd, const float distanceToLine) const
Whether a given position is close to a defined line.
pandora::StatusCode ProjectDeltaRayPositions(const TensorType::Element &element, const pandora::HitType hitType, pandora::CartesianPointVector &projectedPositions) const
Use two views of a delta ray pfo to calculate projected positions in a given third view...
HitType
Definition: HitType.h:12
std::vector< pandora::HitType > HitTypeVector
bool IsMuonEndpoint(const TensorType::Element &element, const bool ignoreHitType, const pandora::HitType hitTypeToIgnore=pandora::TPC_VIEW_U) const
Determine whether the matched clusters suggest that the delta ray is at the endpoint of the cosmic ra...
pandora::StatusCode GetMuonCluster(const pandora::PfoList &commonMuonPfoList, const pandora::HitType hitType, const pandora::Cluster *&pMuonCluster) const
Return the cluster of the common cosmic ray pfo in a given view (function demands there to be only on...
static float GetClosestDistance(const pandora::ClusterList &clusterList1, const pandora::ClusterList &clusterList2)
Get closest distance between clusters in a pair of cluster lists.
virtual pandora::StatusCode ReadSettings(const pandora::TiXmlHandle xmlHandle)=0