26 m_defaultFloat(-10.f),
27 m_nHitsToConsider(10),
28 m_maxInitialGapSizeLimit(4.f),
29 m_minLargestGapSizeLimit(2.f)
61 this->
Run(toolFeatureVec, pAlgorithm, pShowerPfo, nuVertex3D, protoShowerMatch, showerStarts3D);
63 if (featureMap.find(featureToolName +
"_initialGapSize") != featureMap.end())
65 std::cout <<
"Already wrote initialGapSize feature into map! Not writing again." << std::endl;
69 featureOrder.push_back(featureToolName +
"_initialGapSize");
70 featureMap[featureToolName +
"_initialGapSize"] = toolFeatureVec[0];
72 if (featureMap.find(featureToolName +
"_largestGapSize") != featureMap.end())
74 std::cout <<
"Already wrote largestGapSize feature into map! Not writing again." << std::endl;
78 featureOrder.push_back(featureToolName +
"_largestGapSize");
79 featureMap[featureToolName +
"_largestGapSize"] = toolFeatureVec[1];
85 const ProtoShowerMatch &protoShowerMatch,
const HitType hitType,
float &initialGapSize,
float &largestGapSize)
const
97 initialGapSize = (nuVertex2D - spineHitVector.front()->GetPositionVector()).GetMagnitude();
102 std::vector<float> longitudinalProjections;
105 longitudinalProjections.push_back(startDirection.
GetDotProduct(pCaloHit->GetPositionVector() - nuVertex2D));
107 std::sort(longitudinalProjections.begin(), longitudinalProjections.end());
109 const unsigned int nIterations(std::min(longitudinalProjections.size(),
static_cast<long unsigned int>(
m_nHitsToConsider)) - 1);
111 for (
unsigned int i = 0; i < nIterations; ++i)
112 largestGapSize = std::max(std::fabs(longitudinalProjections[i] - longitudinalProjections[i + 1]), largestGapSize);
129 return STATUS_CODE_SUCCESS;
136 m_defaultFloat(-10.f),
137 m_spineFitWindow(10),
138 m_nLayersHalfWindow(5),
139 m_pathwayLengthLimit(30.f),
140 m_pathwayScatteringAngle2DLimit(10.f)
150 const float pathwayLength = (nuVertex3D - showerStarts3D.front()).GetMagnitude();
151 const float pathwayScatteringAngle2D = this->
Get2DKink(pAlgorithm, protoShowerMatch, showerStarts3D.back());
164 this->
Run(toolFeatureVec, pAlgorithm, pShowerPfo, nuVertex3D, protoShowerMatch, showerStarts3D);
166 if (featureMap.find(featureToolName +
"_pathwayLength") != featureMap.end())
168 std::cout <<
"Already wrote pathwayLength feature into map! Not writing again." << std::endl;
172 featureOrder.push_back(featureToolName +
"_pathwayLength");
173 featureMap[featureToolName +
"_pathwayLength"] = toolFeatureVec[0];
175 if (featureMap.find(featureToolName +
"_pathwayScatteringAngle2D") != featureMap.end())
177 std::cout <<
"Already wrote pathwayScatteringAngle2D feature into map! Not writing again." << std::endl;
181 featureOrder.push_back(featureToolName +
"_pathwayScatteringAngle2D");
182 featureMap[featureToolName +
"_pathwayScatteringAngle2D"] = toolFeatureVec[1];
202 spinePositions.push_back(pCaloHit->GetPositionVector());
216 return middleScatterAngle;
231 const int minLayer(layerFitResultMap.begin()->first), maxLayer(layerFitResultMap.rbegin()->first);
232 const int nLayersSpanned(1 + maxLayer - minLayer);
239 float showerStartL(0.f), showerStartT(0.f);
240 spineFit.
GetLocalPosition(projectedShowerStart, showerStartL, showerStartT);
249 for (LayerFitResultMap::const_iterator iter = layerFitResultMap.begin(), iterEnd = layerFitResultMap.end(); iter != iterEnd; ++iter)
251 const int layer(iter->first);
253 if (layer < minCentralLayer)
256 if (layer > maxCentralLayer)
260 float openingAngle2D(std::numeric_limits<float>::max());
267 const int testLayer(layer + i);
268 const float rL(spineFit.
GetL(testLayer));
272 CartesianVector firstPosition(0.f, 0.f, 0.f), centralPosition(0.f, 0.f, 0.f), secondPosition(0.f, 0.f, 0.f);
281 const CartesianVector firstDirection((centralPosition - firstPosition).GetUnitVector());
282 const CartesianVector secondDirection((secondPosition - centralPosition).GetUnitVector());
284 const float testOpeningAngle2D(secondDirection.
GetOpeningAngle(firstDirection) * 180.f / M_PI);
286 if (testOpeningAngle2D < openingAngle2D)
288 openingAngle2D = testOpeningAngle2D;
292 if (testOpeningAngle2D > thisHighestOpeningAngle)
294 thisHighestOpeningAngle = openingAngle2D;
295 thisHighestKinkPosition = centralPosition;
301 if (openingAngle2D > highestOpeningAngle)
303 highestOpeningAngle = openingAngle2D;
304 highestKinkPosition = thisHighestKinkPosition;
309 return highestOpeningAngle;
329 return STATUS_CODE_SUCCESS;
336 m_defaultFloat(-10.f),
337 m_defaultRatio(-0.5f),
338 m_spineFitWindow(20),
339 m_showerRadius(14.f),
340 m_showerFitWindow(1000),
342 m_moliereFraction(0.9f),
343 m_maxNHitsLimit(2000.f),
344 m_maxFoundHitRatioLimit(1.5f),
345 m_maxScatterAngleLimit(40.f),
346 m_maxOpeningAngleLimit(20.f),
347 m_maxNuVertexEnergyWeightedMeanRadialDistanceLimit(20.f),
348 m_minShowerStartMoliereRadiusLimit(10.f)
363 foundHitRatioU, scatterAngleU, openingAngleU, nuVertexEnergyAsymmetryU, nuVertexEnergyWeightedMeanRadialDistanceU,
364 showerStartEnergyAsymmetryU, showerStartMoliereRadiusU);
371 foundHitRatioV, scatterAngleV, openingAngleV, nuVertexEnergyAsymmetryV, nuVertexEnergyWeightedMeanRadialDistanceV,
372 showerStartEnergyAsymmetryV, showerStartMoliereRadiusV);
379 foundHitRatioW, scatterAngleW, openingAngleW, nuVertexEnergyAsymmetryW, nuVertexEnergyWeightedMeanRadialDistanceW,
380 showerStartEnergyAsymmetryW, showerStartMoliereRadiusW);
399 minNuVertexEnergyAsymmetry, middleNuVertexEnergyAsymmetry, maxNuVertexEnergyAsymmetry);
401 nuVertexEnergyWeightedMeanRadialDistanceW, minNuVertexEnergyWeightedMeanRadialDistance,
402 middleNuVertexEnergyWeightedMeanRadialDistance, maxNuVertexEnergyWeightedMeanRadialDistance);
404 minShowerStartEnergyAsymmetry, middleShowerStartEnergyAsymmetry, maxShowerStartEnergyAsymmetry);
406 minShowerStartMoliereRadius, middleShowerStartMoliereRadius, maxShowerStartMoliereRadius);
412 featureVector.push_back(maxNuVertexEnergyAsymmetry);
414 featureVector.push_back(maxShowerStartEnergyAsymmetry);
425 this->
Run(toolFeatureVec, pAlgorithm, pShowerPfo, nuVertex3D, protoShowerMatch, showerStarts3D);
427 if (featureMap.find(featureToolName +
"_nShowerHits") != featureMap.end())
429 std::cout <<
"Already wrote nShowerHits feature into map! Not writing again." << std::endl;
433 featureOrder.push_back(featureToolName +
"_nShowerHits");
434 featureMap[featureToolName +
"_nShowerHits"] = toolFeatureVec[0];
436 if (featureMap.find(featureToolName +
"_foundHitRatio") != featureMap.end())
438 std::cout <<
"Already wrote foundHitRatio feature into map! Not writing again." << std::endl;
442 featureOrder.push_back(featureToolName +
"_foundHitRatio");
443 featureMap[featureToolName +
"_foundHitRatio"] = toolFeatureVec[1];
445 if (featureMap.find(featureToolName +
"_scatterAngle") != featureMap.end())
447 std::cout <<
"Already wrote scatterAngle feature into map! Not writing again." << std::endl;
451 featureOrder.push_back(featureToolName +
"_scatterAngle");
452 featureMap[featureToolName +
"_scatterAngle"] = toolFeatureVec[2];
454 if (featureMap.find(featureToolName +
"_openingAngle") != featureMap.end())
456 std::cout <<
"Already wrote openingAngle feature into map! Not writing again." << std::endl;
460 featureOrder.push_back(featureToolName +
"_openingAngle");
461 featureMap[featureToolName +
"_openingAngle"] = toolFeatureVec[3];
463 if (featureMap.find(featureToolName +
"_nuVertexEnergyAsymmetry") != featureMap.end())
465 std::cout <<
"Already wrote nuVertexEnergyAsymmetry feature into map! Not writing again." << std::endl;
469 featureOrder.push_back(featureToolName +
"_nuVertexEnergyAsymmetry");
470 featureMap[featureToolName +
"_nuVertexEnergyAsymmetry"] = toolFeatureVec[4];
472 if (featureMap.find(featureToolName +
"_nuVertexEnergyWeightedMeanRadialDistance") != featureMap.end())
474 std::cout <<
"Already wrote nuVertexEnergyWeightedMeanRadialDistance feature into map! Not writing again." << std::endl;
478 featureOrder.push_back(featureToolName +
"_nuVertexEnergyWeightedMeanRadialDistance");
479 featureMap[featureToolName +
"_nuVertexEnergyWeightedMeanRadialDistance"] = toolFeatureVec[5];
481 if (featureMap.find(featureToolName +
"_showerStartEnergyAsymmetry") != featureMap.end())
483 std::cout <<
"Already wrote showerStartEnergyAsymmetry feature into map! Not writing again." << std::endl;
487 featureOrder.push_back(featureToolName +
"_showerStartEnergyAsymmetry");
488 featureMap[featureToolName +
"_showerStartEnergyAsymmetry"] = toolFeatureVec[6];
490 if (featureMap.find(featureToolName +
"_showerStartMoliereRadius") != featureMap.end())
492 std::cout <<
"Already wrote showerStartMoliereRadius feature into map! Not writing again." << std::endl;
496 featureOrder.push_back(featureToolName +
"_showerStartMoliereRadius");
497 featureMap[featureToolName +
"_showerStartMoliereRadius"] = toolFeatureVec[7];
504 float &nHits,
float &foundHitRatio,
float &scatterAngle,
float &openingAngle,
float &nuVertexEnergyAsymmetry,
505 float &nuVertexEnergyWeightedMeanRadialDistance,
float &showerStartEnergyAsymmetry,
float &showerStartMoliereRadius)
512 const bool isDownstream(showerStart2D.
GetZ() > nuVertex2D.
GetZ());
522 for (
const CaloHit *
const pCaloHit : spineHitList)
523 spinePositions.push_back(pCaloHit->GetPositionVector());
531 this->
BuildViewShower(pShowerPfo, spineFitResult, hitType, showerStart2D, nuVertex2D, postShowerHitList, postShowerPositions);
533 this->
GetShowerHitVariables(spineHitList, postShowerHitList, pShowerPfo, hitType, nHits, foundHitRatio);
543 for (
const CaloHit *
const pCaloHit : viewHitList)
545 if (std::find(postShowerHitList.begin(), postShowerHitList.end(), pCaloHit) != postShowerHitList.end())
553 if (((isDownstream && (l > 0.f)) || (!isDownstream && (l < 0.f))) && (t <
m_showerRadius))
555 postShowerHitList.push_back(pCaloHit);
556 postShowerPositions.push_back(pCaloHit->GetPositionVector());
560 this->
GetShowerHitVariables(spineHitList, postShowerHitList, pShowerPfo, hitType, nHits, foundHitRatio);
567 spineFitResult, postShowerHitList, isDownstream, nuVertex2D, nuVertexEnergyAsymmetry, nuVertexEnergyWeightedMeanRadialDistance);
570 showerFitResult, postShowerHitList, isShowerDownstream, showerStartEnergyAsymmetry, showerStartMoliereRadius);
583 float lShowerStart(0.f), tShowerStart(0.f);
587 const int showerStartLayer(spineFit.
GetLayer(lShowerStart));
588 int closestLayer(std::numeric_limits<int>::max());
590 for (
const auto &entry : layerFitResultMap)
592 if (std::fabs(entry.first - showerStartLayer) < std::fabs(entry.first - closestLayer))
593 closestLayer = entry.first;
596 const float gradient(layerFitResultMap.at(closestLayer).GetGradient());
602 const bool isDownstream(showerStart2D.
GetZ() > nuVertex2D.
GetZ());
607 for (
const CaloHit *
const pCaloHit : caloHitList)
614 if (((isDownstream && (l > 0.f)) || (!isDownstream && (l < 0.f))) && (t <
m_showerRadius))
616 postShowerHitList.push_back(pCaloHit);
617 postShowerPositions.push_back(pCaloHit->GetPositionVector());
627 int foundHits(spineHitList.size());
629 for (
const CaloHit *
const pCaloHit : postShowerHitList)
631 if (std::find(spineHitList.begin(), spineHitList.end(), pCaloHit) == spineHitList.end())
638 foundHitRatio =
static_cast<float>(foundHits) /
static_cast<float>(viewHitList.size());
639 nHits = postShowerHitList.size();
647 const bool isDownstream(showerStart2D.
GetZ() > nuVertex2D.
GetZ());
656 scatterAngle = streamCorrectedConnectionPathwayDirection.
GetOpeningAngle(streamCorrectedShowerDirection) * 180.f / M_PI;
669 std::map<int, float> positiveEdges, negativeEdges;
671 for (
const CaloHit *
const pCaloHit : postShowerHitList)
673 const CartesianVector position(pCaloHit->GetPositionVector() - showerStart2D);
678 std::map<int, float> &edgeMap(orthoL > 0.f ? positiveEdges : negativeEdges);
680 const int lIndex(std::floor(thisL /
m_edgeStep));
682 edgeMap[lIndex] = (edgeMap.find(lIndex) == edgeMap.end() ? thisT : std::max(edgeMap[lIndex], thisT));
687 for (
auto &entry : positiveEdges)
688 positiveEdgePositions.push_back(
CartesianVector(entry.second, 0.f, entry.first));
690 for (
auto &entry : negativeEdges)
691 negativeEdgePositions.push_back(
CartesianVector(entry.second, 0.f, entry.first));
702 showerStart2D + (directionAxis * positiveMinLayer.
GetZ()) + (orthoAxis * positiveMinLayer.
GetX()));
704 showerStart2D + (directionAxis * positiveMaxLayer.
GetZ()) + (orthoAxis * positiveMaxLayer.
GetX()));
706 showerStart2D + (directionAxis * negativeMinLayer.
GetZ()) - (orthoAxis * negativeMinLayer.
GetX()));
708 showerStart2D + (directionAxis * negativeMaxLayer.
GetZ()) - (orthoAxis * negativeMaxLayer.
GetX()));
710 const CartesianVector positiveEdgeVector((globalPositiveMaxLayer - globalPositiveMinLayer).GetUnitVector());
711 const CartesianVector negativeEdgeVector((globalNegativeMaxLayer - globalNegativeMinLayer).GetUnitVector());
713 const float positiveOpeningAngle = directionAxis.
GetOpeningAngle(positiveEdgeVector) * 180.f / M_PI;
714 const float negativeOpeningAngle = directionAxis.
GetOpeningAngle(negativeEdgeVector) * 180.f / M_PI;
716 openingAngle = std::max(positiveOpeningAngle, negativeOpeningAngle);
726 const bool isDownstream,
const CartesianVector &nuVertex2D,
float &nuVertexEnergyAsymmetry,
float &nuVertexEnergyWeightedMeanRadialDistance)
731 float totalEnergy(0.f);
734 nuVertexEnergyAsymmetry = 0.f;
736 for (
const CaloHit *
const pCaloHit : postShowerHitList)
738 const float hitEnergy(std::fabs(pCaloHit->GetElectromagneticEnergy()));
740 totalEnergy += hitEnergy;
742 const CartesianVector position(pCaloHit->GetPositionVector() - nuVertex2D);
743 const float thisL(orthoAxis.GetDotProduct(position));
745 nuVertexEnergyAsymmetry += (thisL < 0.f) ? (-1.f * hitEnergy) : hitEnergy;
748 nuVertexEnergyAsymmetry = (totalEnergy < std::numeric_limits<float>::epsilon()) ?
m_defaultRatio : (nuVertexEnergyAsymmetry / totalEnergy);
749 nuVertexEnergyAsymmetry = std::fabs(nuVertexEnergyAsymmetry);
752 nuVertexEnergyWeightedMeanRadialDistance = 0.f;
754 for (
const CaloHit *
const pCaloHit : postShowerHitList)
756 const CartesianVector position(pCaloHit->GetPositionVector() - nuVertex2D);
757 const float hitEnergy(std::fabs(pCaloHit->GetElectromagneticEnergy()));
759 nuVertexEnergyWeightedMeanRadialDistance += (directionAxis.GetCrossProduct(position).GetMagnitude() * hitEnergy);
762 nuVertexEnergyWeightedMeanRadialDistance =
763 (totalEnergy < std::numeric_limits<float>::epsilon()) ?
m_defaultFloat : nuVertexEnergyWeightedMeanRadialDistance / totalEnergy;
769 const CaloHitList &postShowerHitList,
const bool isShowerDownstream,
float &showerStartEnergyAsymmetry,
float &showerStartMoliereRadius)
776 float totalEnergy(0.f);
779 showerStartEnergyAsymmetry = 0.f;
781 for (
const CaloHit *
const pCaloHit : postShowerHitList)
783 const float hitEnergy(std::fabs(pCaloHit->GetElectromagneticEnergy()));
785 totalEnergy += hitEnergy;
787 const CartesianVector position(pCaloHit->GetPositionVector() - fitShowerStart);
788 const float thisL(orthoAxis.GetDotProduct(position));
790 showerStartEnergyAsymmetry += (thisL < 0.f) ? (-1.f * hitEnergy) : hitEnergy;
793 showerStartEnergyAsymmetry = (totalEnergy < std::numeric_limits<float>::epsilon()) ?
m_defaultRatio : (showerStartEnergyAsymmetry / totalEnergy);
794 showerStartEnergyAsymmetry = std::fabs(showerStartEnergyAsymmetry);
799 CaloHitVector showerStartPostShowerHitVector(postShowerHitList.begin(), postShowerHitList.end());
801 std::sort(showerStartPostShowerHitVector.begin(), showerStartPostShowerHitVector.end(),
802 [&fitShowerStart, &directionAxis](
const CaloHit *
const pCaloHitA,
const CaloHit *
const pCaloHitB) ->
bool {
803 const CartesianVector positionA(pCaloHitA->GetPositionVector() - fitShowerStart);
804 const CartesianVector positionB(pCaloHitB->GetPositionVector() - fitShowerStart);
806 const float tA(directionAxis.GetCrossProduct(positionA).GetMagnitude());
807 const float tB(directionAxis.GetCrossProduct(positionB).GetMagnitude());
812 float showerStartRunningEnergySum(0.f);
814 for (
const CaloHit *
const pCaloHit : showerStartPostShowerHitVector)
816 const float hitEnergy(std::fabs(pCaloHit->GetElectromagneticEnergy()));
817 showerStartRunningEnergySum += hitEnergy;
821 const CartesianVector position(pCaloHit->GetPositionVector() - fitShowerStart);
822 showerStartMoliereRadius = directionAxis.GetCrossProduct(position).GetMagnitude();
863 return STATUS_CODE_SUCCESS;
870 m_defaultFloat(-10.f),
871 m_caloHitListNameU(
"CaloHitListU"),
872 m_caloHitListNameV(
"CaloHitListV"),
873 m_caloHitListNameW(
"CaloHitListW"),
874 m_maxTransverseDistance(0.75f),
876 m_maxHitSeparation(1.f),
877 m_maxTrackFraction(0.8f)
887 float nAmbiguousViews(0.f);
894 maxUnaccountedEnergy = std::max(maxUnaccountedEnergy, unaccountedHitEnergyU);
897 maxUnaccountedEnergy = std::max(maxUnaccountedEnergy, unaccountedHitEnergyV);
900 maxUnaccountedEnergy = std::max(maxUnaccountedEnergy, unaccountedHitEnergyW);
902 featureVector.push_back(nAmbiguousViews);
903 featureVector.push_back(maxUnaccountedEnergy);
913 this->
Run(toolFeatureVec, pAlgorithm, pShowerPfo, nuVertex3D, protoShowerMatch, showerStarts3D);
915 if (featureMap.find(featureToolName +
"_nAmbiguousViews") != featureMap.end())
917 std::cout <<
"Already wrote nAmbiguousViews feature into map! Not writing again." << std::endl;
921 featureOrder.push_back(featureToolName +
"_nAmbiguousViews");
922 featureMap[featureToolName +
"_nAmbiguousViews"] = toolFeatureVec[0];
924 if (featureMap.find(featureToolName +
"_maxUnaccountedEnergy") != featureMap.end())
926 std::cout <<
"Already wrote maxUnaccountedEnergy feature into map! Not writing again." << std::endl;
930 featureOrder.push_back(featureToolName +
"_maxUnaccountedEnergy");
931 featureMap[featureToolName +
"_maxUnaccountedEnergy"] = toolFeatureVec[1];
938 nAmbiguousViews = 0.f;
941 nAmbiguousViews += (nAmbiguousHitsU == 0) ? 0.f : 1.f;
944 nAmbiguousViews += (nAmbiguousHitsV == 0) ? 0.f : 1.f;
947 nAmbiguousViews += (nAmbiguousHitsW == 0) ? 0.f : 1.f;
955 std::map<int, CaloHitList> ambiguousHitSpines;
962 this->
BuildAmbiguousSpines(pAlgorithm, hitType, protoShower, nuVertex2D, ambiguousHitSpines, hitsToExcludeInEnergyCalcs);
964 if (ambiguousHitSpines.empty())
968 float startL(-std::numeric_limits<float>::max());
969 float ambiguousHitEnergyMean(0.f);
975 const float thisL(startDirection.
GetDotProduct(pAmbiguousCaloHit->GetPositionVector() - nuVertex2D));
980 ambiguousHitEnergyMean += pAmbiguousCaloHit->GetElectromagneticEnergy() * 1000.f;
986 float otherEnergyMeanSum(0.f);
988 for (
const auto &entry : ambiguousHitSpines)
990 int nOtherEnergyHits(0);
991 float otherEnergyMean(0.f);
993 for (
const CaloHit *
const pOtherCaloHit : entry.second)
995 if (std::find(hitsToExcludeInEnergyCalcs.begin(), hitsToExcludeInEnergyCalcs.end(), pOtherCaloHit) != hitsToExcludeInEnergyCalcs.end())
998 otherEnergyMean += pOtherCaloHit->GetElectromagneticEnergy() * 1000.f;
1002 if (nOtherEnergyHits == 0)
1005 otherEnergyMean /=
static_cast<float>(nOtherEnergyHits);
1006 otherEnergyMeanSum += otherEnergyMean;
1010 float spineEnergyMean(0.f);
1011 unsigned int nSpineEnergyHits(0);
1019 const float thisL(startDirection.
GetDotProduct(pSpineCaloHit->GetPositionVector() - nuVertex2D));
1023 spineEnergyMean += pSpineCaloHit->GetElectromagneticEnergy() * 1000.f;
1028 if (nSpineEnergyHits == 0)
1031 spineEnergyMean /=
static_cast<float>(nSpineEnergyHits);
1032 unaccountedHitEnergy = ambiguousHitEnergyMean - otherEnergyMeanSum - spineEnergyMean;
1044 if (this->
GetHitListOfType(pAlgorithm, hitType, pCaloHitList) != STATUS_CODE_SUCCESS)
1047 std::map<int, CaloHitList> ambiguousHitSpinesTemp;
1049 for (
const CaloHit *
const pCaloHit : *pCaloHitList)
1061 const CartesianVector displacement(pCaloHit->GetPositionVector() - nuVertex2D);
1063 const float thisL(significantDirection.
GetDotProduct(displacement));
1068 ambiguousHitSpinesTemp[i].push_back(pCaloHit);
1072 hitsToExcludeInEnergyCalcs.push_back(pCaloHit);
1076 if (ambiguousHitSpinesTemp.empty())
1080 for (
const auto &entry : ambiguousHitSpinesTemp)
1084 if (continuousSpine.size() > 0)
1085 ambiguousHitSpines[entry.first] = continuousSpine;
1096 STATUS_CODE_SUCCESS, STATUS_CODE_NOT_INITIALIZED, !=,
PandoraContentApi::GetList(*pAlgorithm, typeHitListName, pCaloHitList));
1098 if (!pCaloHitList || pCaloHitList->empty())
1099 return STATUS_CODE_NOT_INITIALIZED;
1101 return STATUS_CODE_SUCCESS;
1111 CaloHitVector caloHitVector(caloHitList.begin(), caloHitList.end());
1114 for (
unsigned int i = 0; i < caloHitVector.size(); ++i)
1117 connectedHitList.push_back(caloHitVector[i]);
1128 for (
unsigned int j = (i + 1); j < caloHitVector.size(); ++j)
1130 const CaloHit *
const pCaloHit(caloHitVector[j]);
1132 if (std::find(connectedHitList.begin(), connectedHitList.end(), pCaloHit) != connectedHitList.end())
1138 if (
static_cast<float>(connectedHitList.size()) <
static_cast<float>(caloHitVector.size() *
m_maxTrackFraction))
1141 connectedHitList.push_back(pCaloHit);
1149 if (connectedHitList.size() >= 2)
1151 continuousHitList.insert(continuousHitList.begin(), connectedHitList.begin(), connectedHitList.end());
1156 return continuousHitList;
1185 return STATUS_CODE_SUCCESS;
Header file for the cluster helper class.
Header file for the connection pathway helper class.
Header file for the geometry helper class.
Header file for the pfo helper class.
Header file for the ProtoShower class.
Header file defining status codes and relevant preprocessor macros.
#define PANDORA_THROW_RESULT_IF_AND_IF(StatusCode1, StatusCode2, Operator, Command)
#define PANDORA_RETURN_RESULT_IF_AND_IF(StatusCode1, StatusCode2, Operator, Command)
static pandora::StatusCode GetList(const pandora::Algorithm &algorithm, const std::string &listName, const T *&pT)
Get a named list.
float m_defaultFloat
Default float value.
bool GetViewAmbiguousHitVariables(const pandora::Algorithm *const pAlgorithm, const ProtoShowerMatch &protoShowerMatch, const pandora::HitType hitType, const pandora::CartesianVector &nuVertex3D, float &unaccountedHitEnergy)
Calculate the ambiguous region variables for the input view.
std::string m_caloHitListNameU
The event U view hit list.
float m_maxTransverseDistance
The max. proximity of a hits, included in a trajectory energy calcs.
float m_maxTrackFraction
The fraction of found hits which are considered in the energy calcs.
unsigned int m_maxSampleHits
The max. number of hits considered in the spine energy calcs.
pandora::StatusCode ReadSettings(const pandora::TiXmlHandle xmlHandle)
Read the algorithm settings.
pandora::StatusCode GetHitListOfType(const pandora::Algorithm *const pAlgorithm, const pandora::HitType hitType, const pandora::CaloHitList *&pCaloHitList) const
Obtain the event hit list of a given view.
pandora::CaloHitList FindAmbiguousContinuousSpine(const pandora::CaloHitList &caloHitList, const pandora::CaloHitList &ambiguousHitList, const pandora::CartesianVector &nuVertex2D)
Determine a continuous pathway of an ambigous particle's spine hits.
void BuildAmbiguousSpines(const pandora::Algorithm *const pAlgorithm, const pandora::HitType hitType, const ProtoShower &protoShower, const pandora::CartesianVector &nuVertex2D, std::map< int, pandora::CaloHitList > &ambiguousHitSpines, pandora::CaloHitList &hitsToExcludeInEnergyCalcs)
Determine the spine hits of the particles with which the ambiguous hits are shared.
float m_maxHitSeparation
The max. separation of connected hits.
std::string m_caloHitListNameV
The event V view hit list.
void CalculateNAmbiguousViews(const ProtoShowerMatch &protoShowerMatch, float &nAmbiguousViews)
Count the number of views with ambiguous hits.
void Run(LArMvaHelper::MvaFeatureVector &featureVector, const pandora::Algorithm *const pAlgorithm, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::CartesianPointVector &showerStarts3D)
std::string m_caloHitListNameW
The event W view hit list.
AmbiguousRegionFeatureTool()
Default constructor.
const pandora::CartesianVector & GetStartDirection() const
Get the start direction of the connection pathway.
float m_pathwayLengthLimit
pathwayLengthLimit max. limit
pandora::StatusCode ReadSettings(const pandora::TiXmlHandle xmlHandle)
Read the algorithm settings.
float GetLargest2DKinkFromView(const pandora::Algorithm *const pAlgorithm, const TwoDSlidingFitResult &spineFit, const pandora::HitType hitType, const pandora::CartesianVector &showerStart3D) const
Obtain a cautious estimate of the largest 2D deflection of a connection pathway in a given view.
float m_defaultFloat
Default float value.
void Run(LArMvaHelper::MvaFeatureVector &featureVector, const pandora::Algorithm *const pAlgorithm, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::CartesianPointVector &showerStarts3D)
unsigned int m_spineFitWindow
The spine fit window.
int m_nLayersHalfWindow
The half window of each segment.
ConnectionRegionFeatureTool()
Default constructor.
float Get2DKink(const pandora::Algorithm *const pAlgorithm, const ProtoShowerMatch &protoShowerMatch, const pandora::CartesianVector &showerStart3D) const
Obtain a cautious estimate of the largest 2D deflection of the connection pathway.
float m_pathwayScatteringAngle2DLimit
pathwayScatteringAngle2DLimit max. limit
float m_maxInitialGapSizeLimit
maxInitialGapSizeLimit max. limit
float m_minLargestGapSizeLimit
minLargestGapSizeLimit max. limit
float m_defaultFloat
Default float value.
pandora::StatusCode ReadSettings(const pandora::TiXmlHandle xmlHandle)
Read the algorithm settings.
void GetViewInitialRegionVariables(const pandora::Algorithm *const pAlgorithm, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::HitType hitType, float &initialGapSize, float &largestGapSize) const
Calculate the initial region variables for the input view.
void Run(LArMvaHelper::MvaFeatureVector &featureVector, const pandora::Algorithm *const pAlgorithm, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::CartesianPointVector &showerStarts3D)
InitialRegionFeatureTool()
Default constructor.
unsigned int m_nHitsToConsider
The number of hits which defines the initial region.
static float GetClosestDistance(const pandora::ClusterList &clusterList1, const pandora::ClusterList &clusterList2)
Get closest distance between clusters in a pair of cluster lists.
SortByDistanceToPoint class.
static void GetMinMiddleMax(const float value1, const float value2, const float value3, float &minValue, float &middleValue, float &maxValue)
Determine the lowest, median and highest value from an input of three numbers.
static float GetWirePitch(const pandora::Pandora &pandora, const pandora::HitType view, const float maxWirePitchDiscrepancy=0.01)
Return the wire pitch.
static pandora::CartesianVector ProjectPosition(const pandora::Pandora &pandora, const pandora::CartesianVector &position3D, const pandora::HitType view)
Project 3D position into a given 2D view.
MvaTypes::MvaFeatureVector MvaFeatureVector
MvaTypes::MvaFeatureMap MvaFeatureMap
static void GetCaloHits(const pandora::PfoList &pfoList, const pandora::HitType &hitType, pandora::CaloHitList &caloHitList)
Get a list of calo hits of a particular hit type from a list of pfos.
const pandora::CaloHitList & GetAmbiguousHitList() const
Get the ambiguous hit list.
const ConnectionPathway & GetConnectionPathway() const
Get the connection pathway.
const pandora::CartesianPointVector & GetAmbiguousDirectionVector() const
Get the ambiguous direction vector.
const pandora::CaloHitList & GetSpineHitList() const
Get the spine hit list.
const ProtoShower & GetProtoShowerV() const
Get the V view ProtoShower.
const ProtoShower & GetProtoShowerW() const
Get the W view ProtoShower.
const ProtoShower & GetProtoShowerU() const
Get the U view ProtoShower.
ShowerRegionFeatureTool()
Default constructor.
unsigned int m_spineFitWindow
The spine fit window.
void GetViewShowerRegionVariables(const pandora::Algorithm *const pAlgorithm, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::HitType hitType, const pandora::CartesianVector &showerStart3D, float &nHits, float &foundHitRatio, float &scatterAngle, float &openingAngle, float &nuVertexEnergyAsymmetry, float &nuVertexEnergyWeightedMeanRadialDistance, float &showerStartEnergyAsymmetry, float &showerStartMoliereRadius)
Calculate the shower region variables for the input view.
void CalculateViewNuVertexConsistencyVariables(const TwoDSlidingFitResult &spineFitResult, const pandora::CaloHitList &postShowerHitList, const bool isDownstream, const pandora::CartesianVector &nuVertex2D, float &nuVertexEnergyAsymmetry, float &nuVertexEnergyWeightedMeanRadialDistance)
Evaluate the neutrino vertex consistency variables.
void GetShowerHitVariables(const pandora::CaloHitList &spineHitList, const pandora::CaloHitList &postShowerHitList, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::HitType hitType, float &nHits, float &foundHitRatio)
Evaluate the variables associated with the shower region hit multiplicity.
void BuildViewShower(const pandora::ParticleFlowObject *const pShowerPfo, const TwoDSlidingFitResult &spineFit, const pandora::HitType hitType, const pandora::CartesianVector &showerStart2D, const pandora::CartesianVector &nuVertex2D, pandora::CaloHitList &postShowerHitList, pandora::CartesianPointVector &postShowerPositions)
Collect the shower region hits in a given view.
float m_maxFoundHitRatioLimit
maxFoundHitRatio max. limit
void CalculateViewOpeningAngle(const TwoDSlidingFitResult &showerFitResult, const pandora::CaloHitList &postShowerHitList, const pandora::CartesianVector &showerStart2D, float &openingAngle)
Calculate the opening angle of the shower region.
float m_moliereFraction
The energy fraction which corresponds to minShowerStartMoliereRadius.
float m_maxScatterAngleLimit
maxScatterAngle max. limit
float m_showerRadius
The max. separation distance between a shower region hit and the shower core.
unsigned int m_showerFitWindow
The shower fit window.
float m_defaultRatio
Default float value for ratios.
float m_defaultFloat
Default float value.
void CalculateViewShowerStartConsistencyVariables(const TwoDSlidingFitResult &showerFitResult, const pandora::CaloHitList &postShowerHitList, const bool isShowerDownstream, float &showerStartEnergyAsymmetry, float &showerStartMoliereRadius)
Evaluate the shower start consistency variables.
void Run(LArMvaHelper::MvaFeatureVector &featureVector, const pandora::Algorithm *const pAlgorithm, const pandora::ParticleFlowObject *const pShowerPfo, const pandora::CartesianVector &nuVertex3D, const ProtoShowerMatch &protoShowerMatch, const pandora::CartesianPointVector &showerStarts3D)
pandora::StatusCode ReadSettings(const pandora::TiXmlHandle xmlHandle)
Read the algorithm settings.
float m_maxNuVertexEnergyWeightedMeanRadialDistanceLimit
maxNuVertexEnergyWeightedMeanRadialDistance max. limit
float m_maxNHitsLimit
maxNHits max. limit
void CalculateViewScatterAngle(const pandora::CartesianVector &nuVertex2D, const TwoDSlidingFitResult &spineFitResult, const pandora::CartesianVector &showerStart2D, const TwoDSlidingFitResult &showerFitResult, float &scatterAngle)
Calculate the connection pathway-shower region scatter angle.
float m_edgeStep
The binning of the shower boundaries.
float m_minShowerStartMoliereRadiusLimit
minShowerStartMoliereRadius max. limit
float m_maxOpeningAngleLimit
maxOpeningAngle max. limit
TwoDSlidingFitResult class.
float GetL(const int layer) const
Get longitudinal coordinate for a given sliding linear fit layer number.
pandora::CartesianVector GetGlobalMinLayerPosition() const
Get global position corresponding to the fit result in minimum fit layer.
void GetLocalPosition(const pandora::CartesianVector &position, float &rL, float &rT) const
Get local sliding fit coordinates for a given global position.
const LayerFitResultMap & GetLayerFitResultMap() const
Get the layer fit result map.
pandora::StatusCode GetGlobalFitPosition(const float rL, pandora::CartesianVector &position) const
Get global fit position for a given longitudinal coordinate.
float GetLayerPitch() const
Get the layer pitch, units cm.
pandora::CartesianVector GetGlobalMinLayerDirection() const
Get global direction corresponding to the fit result in minimum fit layer.
pandora::CartesianVector GetGlobalMaxLayerPosition() const
Get global position corresponding to the fit result in maximum fit layer.
int GetLayer(const float rL) const
Get layer number for given sliding linear fit longitudinal coordinate.
void GetGlobalDirection(const float dTdL, pandora::CartesianVector &direction) const
Get global direction coordinates for given sliding linear fit gradient.
pandora::CartesianVector GetGlobalMaxLayerDirection() const
Get global direction corresponding to the fit result in maximum fit layer.
Algorithm class. Algorithm addresses are held only by the algorithm manager. They have a fully define...
const CartesianVector & GetPositionVector() const
Get the position vector of center of calorimeter cell, units mm.
float GetX() const
Get the cartesian x coordinate.
float GetZ() const
Get the cartesian z coordinate.
float GetDotProduct(const CartesianVector &rhs) const
Get the dot product of the cartesian vector with a second cartesian vector.
float GetMagnitude() const
Get the magnitude.
CartesianVector GetCrossProduct(const CartesianVector &rhs) const
Get the cross product of the cartesian vector with a second cartesian vector.
float GetOpeningAngle(const CartesianVector &rhs) const
Get the opening angle of the cartesian vector with respect to a second cartesian vector.
ParticleFlowObject class.
const Pandora & GetPandora() const
Get the associated pandora instance.
StatusCodeException class.
static StatusCode ReadValue(const TiXmlHandle &xmlHandle, const std::string &xmlElementName, T &t)
Read a value from an xml element.
std::map< int, LayerFitResult > LayerFitResultMap
HitType
Calorimeter hit type enum.
std::vector< const CaloHit * > CaloHitVector
std::vector< std::string > StringVector
std::vector< CartesianVector > CartesianPointVector
MANAGED_CONTAINER< const CaloHit * > CaloHitList
StatusCode
The StatusCode enum.