From 22510b55dbd1e02e3d9b79d6f56c8eb1afe05a40 Mon Sep 17 00:00:00 2001 From: Tim Martin <Tim.Martin@cern.ch> Date: Tue, 3 Mar 2020 14:55:25 +0100 Subject: [PATCH] Use ElementLinkVector --- .../DecisionHandling/src/ComboHypo.cxx | 61 ++++++++---------- .../DecisionHandling/src/ComboHypo.h | 11 ++-- .../src/ComboHypoCombination.cxx | 28 -------- .../src/ComboHypoCombination.h | 64 ------------------- 4 files changed, 30 insertions(+), 134 deletions(-) delete mode 100644 Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.cxx delete mode 100644 Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.h diff --git a/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.cxx b/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.cxx index 9b146ee19a5..06807962114 100644 --- a/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.cxx +++ b/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.cxx @@ -138,7 +138,7 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { DecisionIDContainer passing; // this map is filled with the count of positive decisions from each input - CombinationMap dmap; + LegDecisionsMap dmap; ATH_CHECK( fillDecisionsMap( dmap, context ) ); @@ -153,7 +153,7 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { allDecisionIds.insert(requiredDecisionID); bool overallDecision = true; - DecisionIDContainer uniqueDecisions; + std::set<uint32_t> uniqueDecisionFeatures; // Check multiplicity of each leg for ( size_t legIndex = 0; legIndex < multiplicityPerLeg.size(); ++legIndex ) { @@ -171,7 +171,7 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { const DecisionID requiredDecisionIDLeg = legId.numeric(); ATH_MSG_DEBUG("Container " << legIndex << ", looking at leg : " << legId ); - CombinationMap::const_iterator it = dmap.find(requiredDecisionIDLeg); + LegDecisionsMap::const_iterator it = dmap.find(requiredDecisionIDLeg); if ( it == dmap.end() ) { overallDecision = false; break; @@ -179,7 +179,7 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { //check this leg of the chain passes with required multiplicity - const size_t observedMultiplicity = it->second.getCombinations().size(); + const size_t observedMultiplicity = it->second.size(); ATH_MSG_DEBUG( "Required multiplicity " << requiredMultiplicity << " for leg " << legId << ": observed multiplicity " << observedMultiplicity << " in leg " << legIndex ); @@ -189,22 +189,26 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { } //keep track of the number of unique features - - for (const auto& entry : it->second.getFeatures()){ - if (entry.first == 0) { + for (const ElementLink<DecisionContainer>& dEL : it->second){ + uint32_t featureKey = 0, roiKey = 0; + uint16_t featureIndex = 0, roiIndex = 0; + // NOTE: roiKey, roiIndex not currently used in this discrimination + ATH_CHECK( extractFeatureAndRoI(dEL, featureKey, featureIndex, roiKey, roiIndex) ); + const uint32_t featureHash = (featureKey + featureIndex); + if (featureHash == 0) { ATH_MSG_WARNING("Disregarding feature hash of zero"); continue; } - uniqueDecisions.insert( entry.first ); - // TODO - do something with entry.second (the ROI) + uniqueDecisionFeatures.insert( featureHash ); + // TODO - do something with the ROI } allDecisionIds.insert(requiredDecisionIDLeg); } //check that the multiplicity of unique features is high enough - ATH_MSG_DEBUG("Number of unique decisions: " << uniqueDecisions.size() << ", number of required unique decisions: " << nRequiredUnique); - if ( uniqueDecisions.size() < nRequiredUnique ) { + ATH_MSG_DEBUG("Number of unique features: " << uniqueDecisionFeatures.size() << ", number of required unique decisions: " << nRequiredUnique); + if ( uniqueDecisionFeatures.size() < nRequiredUnique ) { overallDecision = false; } @@ -223,30 +227,29 @@ StatusCode ComboHypo::execute(const EventContext& context ) const { return StatusCode::SUCCESS; } -StatusCode ComboHypo::extractFeatureAndRoI(const Decision* d, const std::string& input, +StatusCode ComboHypo::extractFeatureAndRoI(const ElementLink<DecisionContainer>& dEL, uint32_t& featureKey, uint16_t& featureIndex, uint32_t& roiKey, uint16_t& roiIndex) const { uint32_t featureClid = 0; // Note: Unused. We don't care what the type of the feature is here - const bool result = d->typelessGetObjectLink(featureString(), featureKey, featureClid, featureIndex); + const bool result = (*dEL)->typelessGetObjectLink(featureString(), featureKey, featureClid, featureIndex); if (!result) { - ATH_MSG_ERROR("Did not find the feature for Input:" << input << " Element:" << d->index()); + ATH_MSG_ERROR("Did not find the feature for " << dEL.dataID() << " index " << dEL.index()); } // Try and get seeding ROI data too. Don't need to be type-less here if (m_requireUniqueROI) { - LinkInfo<TrigRoiDescriptorCollection> roiSeedLI = findLink<TrigRoiDescriptorCollection>(d, initialRoIString()); + LinkInfo<TrigRoiDescriptorCollection> roiSeedLI = findLink<TrigRoiDescriptorCollection>((*dEL), initialRoIString()); if (roiSeedLI.isValid()) { roiKey = roiSeedLI.link.key(); roiIndex = roiSeedLI.link.index(); } else { - ATH_MSG_ERROR("Did not find a seeding ROI for Input:" << input << " Element:" << d->index()); + ATH_MSG_ERROR("Did not find a seeding ROI for " << dEL.dataID() << " index " << dEL.index()); } } return StatusCode::SUCCESS; } -StatusCode ComboHypo::fillDecisionsMap( CombinationMap & dmap, const EventContext& context) const { - +StatusCode ComboHypo::fillDecisionsMap( LegDecisionsMap & dmap, const EventContext& context) const { for ( size_t inputContainerIndex = 0; inputContainerIndex < m_inputs.size(); ++inputContainerIndex ) { auto inputHandle = SG::makeHandle( m_inputs.at(inputContainerIndex), context ); if ( !inputHandle.isValid() ) { @@ -266,14 +269,7 @@ StatusCode ComboHypo::fillDecisionsMap( CombinationMap & dmap, const EventConte } ATH_MSG_DEBUG( " +++ " << HLT::Identifier( id ) ); - // Obtain unique but type-less key & index identifiers for this Decision node's "Feature" - // and (if m_requireUniqueROI) its initialRoI. - // Allows us to check object uniqueness and prevent multiple objects from the same RoI satisfying one leg. - uint32_t featureKey = 0, roiKey = 0; - uint16_t featureIndex = 0, roiIndex = 0; - ATH_CHECK( extractFeatureAndRoI(decision, inputHandle.key(), featureKey, featureIndex, roiKey, roiIndex) ); - - dmap[id].add(inputContainerIndex, decision->index(), featureKey, featureIndex, roiKey, roiIndex); + dmap[id].push_back( TrigCompositeUtils::decisionToElementLink(decision, context) ); } } } @@ -284,15 +280,10 @@ StatusCode ComboHypo::fillDecisionsMap( CombinationMap & dmap, const EventConte size_t legCount = 0; for (const auto& entry: dmap){ ATH_MSG_DEBUG("leg ["<<legCount<<"]: "); - const std::vector<std::pair<uint32_t,uint16_t>>& combinations = entry.second.getCombinations(); - ATH_MSG_DEBUG(" +++ " << HLT::Identifier( entry.first ) <<" mult: "<< combinations.size()); - for (const auto& comb : combinations){ - ATH_MSG_DEBUG(" Comb: (ContainerIndex:"<<comb.first<<", DecisionElementIndex:"<<comb.second<<")"); - } - const std::vector<std::pair<uint32_t,uint32_t>>& featureMap = entry.second.getFeatures(); - ATH_MSG_DEBUG("FeatureMap: found " << featureMap.size() << " entries"); - for (const auto& feat : featureMap) { - ATH_MSG_DEBUG(" Unique Feature Identifier:" << feat.first << ", From ROI Identifier: " << feat.second); + const ElementLinkVector<DecisionContainer>& decisions = entry.second; + ATH_MSG_DEBUG(" +++ " << HLT::Identifier( entry.first ) <<" Number Decisions: "<< decisions.size()); + for (const ElementLink<DecisionContainer>& d : decisions){ + ATH_MSG_DEBUG(" Decision: (ContainerKey:"<<d.key()<<", DecisionElementIndex:"<<d.index()<<")"); } legCount++; } diff --git a/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.h b/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.h index 04b4f704d75..2d2670a888d 100644 --- a/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.h +++ b/Trigger/TrigSteer/DecisionHandling/src/ComboHypo.h @@ -8,8 +8,6 @@ #include "AthenaBaseComps/AthReentrantAlgorithm.h" #include "DecisionHandling/TrigCompositeUtils.h" -#include "ComboHypoCombination.h" - // STL includes #include <string> #include <utility> @@ -55,21 +53,20 @@ private: * @brief For a given Decision node from a HypoAlg, extracts type-less identification data on the node's Feature and seeding ROI. * @param[in] d The Decision node from the HypoAlg, expected to have a "feature" link attached to it. * Expected to be able to locate a "initialRoI" in its history if RequireUniqueROI=True. - * @param[in] input Name of the collection the Decision comes from, used for error printing only. * @param[out] featureKey Type-less SG Key hash of the collection hosting the Decision node's feature . * @param[out] featureIndex Index inside the featureKey collection. * @param[out] roiKey Type-less SG Key hash of the collection hosting the Decision node's initial ROI collection. * @param[out] roiIndex Index inside the roiKey collection. **/ - StatusCode extractFeatureAndRoI(const TrigCompositeUtils::Decision* d, const std::string& input, + StatusCode extractFeatureAndRoI(const ElementLink<TrigCompositeUtils::DecisionContainer>& EL, uint32_t& featureKey, uint16_t& featureIndex, uint32_t& roiKey, uint16_t& roiIndex) const; /** - * @brief iterates over all inputs filling the multiplicity map for each input collection + * @brief iterates over all inputs, associating inputs to legs **/ - typedef std::map<TrigCompositeUtils::DecisionID, ComboHypoCombination> CombinationMap; - StatusCode fillDecisionsMap( CombinationMap& dmap, const EventContext& context) const; + typedef std::map<TrigCompositeUtils::DecisionID, ElementLinkVector<TrigCompositeUtils::DecisionContainer>> LegDecisionsMap; + StatusCode fillDecisionsMap( LegDecisionsMap& dmap, const EventContext& context) const; }; diff --git a/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.cxx b/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.cxx deleted file mode 100644 index 3ccebbd0641..00000000000 --- a/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.cxx +++ /dev/null @@ -1,28 +0,0 @@ -/* - Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration -*/ - -#include "ComboHypoCombination.h" - -void ComboHypoCombination::add(const uint32_t inputContainerID, const uint16_t decisionElementID, - const uint32_t featureContainerKey, const uint16_t featureIndex, - const uint32_t roiContainerKey, const uint16_t roiIndex) -{ - m_combinations.push_back( std::make_pair(inputContainerID, decisionElementID) ); - - const uint32_t featureMapLocation = combineKeyAndIndex(featureContainerKey, featureIndex); - const uint32_t roiPayload = combineKeyAndIndex(roiContainerKey, roiIndex); - m_features.push_back( std::make_pair(featureMapLocation, roiPayload) ); -} - -uint32_t ComboHypoCombination::combineKeyAndIndex(const uint32_t key, const uint16_t index) { - return (key + index); -} - -const std::vector< std::pair<uint32_t,uint16_t> >& ComboHypoCombination::getCombinations() const { - return m_combinations; -} - -const std::vector< std::pair<uint32_t,uint32_t> >& ComboHypoCombination::getFeatures() const { - return m_features; -} diff --git a/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.h b/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.h deleted file mode 100644 index 57d8f68da61..00000000000 --- a/Trigger/TrigSteer/DecisionHandling/src/ComboHypoCombination.h +++ /dev/null @@ -1,64 +0,0 @@ -/* - Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration -*/ -#ifndef DECISIONHANDLING_COMBOHYPOCOMBINATION_H -#define DECISIONHANDLING_COMBOHYPOCOMBINATION_H - -// STL includes -#include <map> -#include <utility> // std::pair -#include <vector> - -/** -* @brief Utility class to assist with the bookkeeping when counting Decision objects which pass -* specific chain-leg requirements. Here Decision nodes are identified by abstract key and index pairs, and these -* node's "Feature" and "initialRoI" by hash values. -* -* This suffices to perform Decision node multiplicity counting, and "Feature"/"initialRoI" uniqueness checks. -**/ -class ComboHypoCombination { -public: - - /** - * @brief Compresses the Feature and ROI type-less ID data into single uint32_t hash values - * and stores this along with the Decision node's key & index in two parallel vectors. - **/ - void add(const uint32_t inputContainerID, const uint16_t decisionElementID, - const uint32_t featureContainerKey, const uint16_t featureIndex, - const uint32_t roiContainerKey, const uint16_t roiIndex); - - /** - * @brief Get the node vector. Each entry corresponds to a Decision node (first: key, second: index) - **/ - const std::vector< std::pair<uint32_t,uint16_t> >& getCombinations() const; - - /** - * @brief Get the features vector. Each entry corresponds to a Decision node's Feature & ROI (first: feature, second: roi) - **/ - const std::vector< std::pair<uint32_t,uint32_t> >& getFeatures() const; - -private: - - /** - * @brief key is a SG hash, so is already well distributed. The hash is incremented by the index - * to create a new per-object hash - **/ - uint32_t combineKeyAndIndex(const uint32_t key, const uint16_t index); - - /** - * @brief Each entry corresponds to a Decision node. - * The first element in the pair is the SG key of the node's collection. - * The second element in the pair is the index inside the collection. - **/ - std::vector< std::pair<uint32_t,uint16_t> > m_combinations; - /** - * @brief Each entry corresponds to the Feature of the node in the parallel m_combinations vector. - * The first element in the pair is a combined hash of the SG key & index of the node's Feature. - * The second element in the pair is a combined hash of the SG key & index of the node's initialRoI - **/ - std::vector< std::pair<uint32_t,uint32_t> > m_features; - -}; - - -#endif // DECISIONHANDLING_COMBOHYPOCOMBINATION_H -- GitLab