diff --git a/PWGDQ/Core/VarManager.h b/PWGDQ/Core/VarManager.h index 230a899d807..a0ecadc93f1 100644 --- a/PWGDQ/Core/VarManager.h +++ b/PWGDQ/Core/VarManager.h @@ -28,6 +28,7 @@ #include "Common/CCDB/TriggerAliases.h" #include "Common/Core/CollisionTypeHelper.h" #include "Common/Core/EventPlaneHelper.h" +#include "Common/Core/fwdtrackUtilities.h" #include "Common/Core/trackUtilities.h" #include "CommonConstants/LHCConstants.h" @@ -134,7 +135,8 @@ class VarManager : public TObject ReducedTrackCollInfo = BIT(24), // TODO: remove it once new reduced data tables are produced for dielectron with ReducedTracksBarrelInfo ReducedMuonCollInfo = BIT(25), // TODO: remove it once new reduced data tables are produced for dielectron with ReducedTracksBarrelInfo MuonRealign = BIT(26), - MuonCovRealign = BIT(27) + MuonCovRealign = BIT(27), + MFTCov = BIT(28) }; enum PairCandidateType { @@ -1081,6 +1083,8 @@ class VarManager : public TObject static void FillPairPropagateMuon(T1 const& muon1, T2 const& muon2, const C& collision, float* values = nullptr); template static void FillGlobalMuonRefit(T1 const& muontrack, T2 const& mfttrack, const C& collision, float* values = nullptr); + template + static void FillGlobalMuonRefitCov(T1 const& muontrack, T2 const& mfttrack, const C& collision, C2 const& mftcov, float* values = nullptr); template static void FillPair(T1 const& t1, T2 const& t2, float* values = nullptr); template @@ -1478,6 +1482,35 @@ void VarManager::FillGlobalMuonRefit(T1 const& muontrack, T2 const& mfttrack, co } } +template +void VarManager::FillGlobalMuonRefitCov(T1 const& muontrack, T2 const& mfttrack, const C& collision, C2 const& mftcov, float* values) +{ + if (!values) { + values = fgValues; + } + if constexpr ((MuonfillMap & MuonCov) > 0) { + if constexpr ((MFTfillMap & MFTCov) > 0) { + o2::dataformats::GlobalFwdTrack propmuon = PropagateMuon(muontrack, collision); + SMatrix5 tpars(mfttrack.x(), mfttrack.y(), mfttrack.phi(), mfttrack.tgl(), mfttrack.signed1Pt()); + std::vector v1{mftcov.cXX(), mftcov.cXY(), mftcov.cYY(), mftcov.cPhiX(), mftcov.cPhiY(), + mftcov.cPhiPhi(), mftcov.cTglX(), mftcov.cTglY(), mftcov.cTglPhi(), mftcov.cTglTgl(), + mftcov.c1PtX(), mftcov.c1PtY(), mftcov.c1PtPhi(), mftcov.c1PtTgl(), mftcov.c1Pt21Pt2()}; + SMatrix55 tcovs(v1.begin(), v1.end()); + o2::track::TrackParCovFwd mft{mfttrack.z(), tpars, tcovs, mfttrack.chi2()}; + + o2::dataformats::GlobalFwdTrack globalRefit = o2::aod::fwdtrackutils::refitGlobalMuonCov(propmuon, mft); + values[kX] = globalRefit.getX(); + values[kY] = globalRefit.getY(); + values[kZ] = globalRefit.getZ(); + values[kTgl] = globalRefit.getTgl(); + values[kPt] = globalRefit.getPt(); + values[kPz] = globalRefit.getPz(); + values[kEta] = globalRefit.getEta(); + values[kPhi] = globalRefit.getPhi(); + } + } +} + template void VarManager::FillBC(T const& bc, float* values) { diff --git a/PWGDQ/TableProducer/tableMakerMC_withAssoc.cxx b/PWGDQ/TableProducer/tableMakerMC_withAssoc.cxx index ad48874301e..a3c257652fd 100644 --- a/PWGDQ/TableProducer/tableMakerMC_withAssoc.cxx +++ b/PWGDQ/TableProducer/tableMakerMC_withAssoc.cxx @@ -111,6 +111,7 @@ constexpr static uint32_t gkMuonRealignFillMapWithCov = VarManager::ObjTypes::Mu // constexpr static uint32_t gkMuonFillMapWithCovAmbi = VarManager::ObjTypes::Muon | VarManager::ObjTypes::MuonCov | VarManager::ObjTypes::AmbiMuon; // constexpr static uint32_t gkTrackFillMapWithAmbi = VarManager::ObjTypes::Track | VarManager::ObjTypes::AmbiTrack; constexpr static uint32_t gkMFTFillMap = VarManager::ObjTypes::TrackMFT; +constexpr static uint32_t gkMFTCovFillMap = VarManager::ObjTypes::TrackMFT | VarManager::ObjTypes::MFTCov; template void PrintBitMap(TMap map, int nbits) @@ -237,13 +238,14 @@ struct TableMakerMC { std::map fMftIndexMap; // key: MFT tracklet global index, value: new MFT tracklet global index std::map fBestMatch; + std::unordered_map map_mfttrackcovs; void init(o2::framework::InitContext& context) { // Check whether barrel or muon are enabled bool isProcessBCenabled = context.mOptions.get("processPP"); bool isBarrelEnabled = (context.mOptions.get("processPP") || context.mOptions.get("processPPBarrelOnly") || context.mOptions.get("processPbPbBarrelOnly") || context.mOptions.get("processPbPbWithFilterBarrelOnly")); - bool isMuonEnabled = (context.mOptions.get("processPP") || context.mOptions.get("processPPMuonOnlyBasic") || context.mOptions.get("processPPMuonOnly") || context.mOptions.get("processPPRealignedMuonOnly") || context.mOptions.get("processPbPbMuonOnly") || context.mOptions.get("processPbPbRealignedMuonOnly")); + bool isMuonEnabled = (context.mOptions.get("processPP") || context.mOptions.get("processPPMuonOnlyBasic") || context.mOptions.get("processPPMuonOnly") || context.mOptions.get("processPPRealignedMuonOnly") || context.mOptions.get("processPbPbMuonOnly") || context.mOptions.get("processPbPbRealignedMuonOnly")) || context.mOptions.get("processPPMuonRefit"); // Make sure at least one process function is enabled if (!(isProcessBCenabled || isBarrelEnabled || isMuonEnabled)) { LOG(fatal) << "No process function was enabled for TableMakerMC. Check it out!!!"; @@ -894,8 +896,8 @@ struct TableMakerMC { } } - template - void skimMuons(TEvent const& collision, TMuons const& muons, FwdTrackAssoc const& muonAssocs, aod::McParticles const& mcTracks, TMFTTracks const& /*mftTracks*/) + template + void skimMuons(TEvent const& collision, TMuons const& muons, FwdTrackAssoc const& muonAssocs, aod::McParticles const& mcTracks, TMFTTracks const& /*mftTracks*/, TMFTCovs const& mfCovs) { // Skim the fwd-tracks (muons) // Loop over the collision-track associations, recompute track properties depending on the collision assigned, and apply track cuts for selection @@ -942,7 +944,12 @@ struct TableMakerMC { } auto mfttrack = muon.template matchMFTTrack_as(); VarManager::FillTrackCollision(muontrack, collision); - VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + auto const& mfttrackcov = mfCovs.rawIteratorAt(map_mfttrackcovs[mfttrack.globalIndex()]); + VarManager::FillGlobalMuonRefitCov(muontrack, mfttrack, collision, mfttrackcov); + } else { + VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + } } else { VarManager::FillTrackCollision(muon, collision); } @@ -1059,16 +1066,23 @@ struct TableMakerMC { VarManager::FillPropagateMuon(muon, collision); } // recalculte pDca and global muon kinematics + int globalClusters = muon.nClusters(); if (static_cast(muon.trackType()) < 2 && fConfigVariousOptions.fRefitGlobalMuon) { auto muontrack = muon.template matchMCHTrack_as(); auto mfttrack = muon.template matchMFTTrack_as(); + globalClusters += mfttrack.nClusters(); VarManager::FillTrackCollision(muontrack, collision); - VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + auto const& mfttrackcov = mfCovs.rawIteratorAt(map_mfttrackcovs[mfttrack.globalIndex()]); + VarManager::FillGlobalMuonRefitCov(muontrack, mfttrack, collision, mfttrackcov); + } else { + VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + } } else { VarManager::FillTrackCollision(muon, collision); } muonBasic(reducedEventIdx, mchIdx, mftIdx, fFwdTrackFilterMap[muon.globalIndex()], VarManager::fgValues[VarManager::kPt], VarManager::fgValues[VarManager::kEta], VarManager::fgValues[VarManager::kPhi], muon.sign(), 0); - muonExtra(muon.nClusters(), VarManager::fgValues[VarManager::kMuonPDca], VarManager::fgValues[VarManager::kMuonRAtAbsorberEnd], + muonExtra(globalClusters, VarManager::fgValues[VarManager::kMuonPDca], VarManager::fgValues[VarManager::kMuonRAtAbsorberEnd], VarManager::fgValues[VarManager::kMuonChi2], muon.chi2MatchMCHMID(), muon.chi2MatchMCHMFT(), muon.matchScoreMCHMFT(), muon.mchBitMap(), muon.midBitMap(), @@ -1090,11 +1104,11 @@ struct TableMakerMC { } // end skimMuons template + typename TMuons, typename TMFTTracks, typename TTrackAssoc, typename TFwdTrackAssoc, typename TMFTTrackAssoc, typename TMFTCov> void fullSkimming(TEvents const& collisions, BCsWithTimestamps const& bcs, TTracks const& tracksBarrel, TMuons const& muons, TMFTTracks const& mftTracks, TTrackAssoc const& trackAssocs, TFwdTrackAssoc const& fwdTrackAssocs, TMFTTrackAssoc const& mftAssocs, - aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) + aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles, TMFTCov const& mftCovs) { // Check whether the run changed and update CCDB if it did if (bcs.size() > 0 && fCurrentRun != bcs.begin().runNumber()) { @@ -1155,6 +1169,7 @@ struct TableMakerMC { // Clear index map and reserve memory for MFT tables if constexpr (static_cast(TMFTFillMap)) { fMftIndexMap.clear(); + map_mfttrackcovs.clear(); mftTrack.reserve(mftTracks.size()); mftTrackExtra.reserve(mftTracks.size()); mftAssoc.reserve(mftTracks.size()); @@ -1173,6 +1188,12 @@ struct TableMakerMC { muonLabels.reserve(muons.size()); } + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + for (auto& mfttrackConv : mftCovs) { + map_mfttrackcovs[mfttrackConv.matchMFTTrackId()] = mfttrackConv.globalIndex(); + } + } + // loop over selected collisions and select the tracks and fwd tracks to be skimmed if (fCollIndexMap.size() > 0) { for (auto const& [origIdx, skimIdx] : fCollIndexMap) { @@ -1192,10 +1213,14 @@ struct TableMakerMC { if (fConfigVariousOptions.fKeepBestMatch) { skimBestMuonMatches(muons); } - skimMuons(collision, muons, groupedMuonIndices, mcParticles, mftTracks); + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + skimMuons(collision, muons, groupedMuonIndices, mcParticles, mftTracks, mftCovs); + } else { + skimMuons(collision, muons, groupedMuonIndices, mcParticles, mftTracks, nullptr); + } } else { auto groupedMuonIndices = fwdTrackAssocs.sliceBy(fwdtrackIndicesPerCollision, origIdx); - skimMuons(collision, muons, groupedMuonIndices, mcParticles, nullptr); + skimMuons(collision, muons, groupedMuonIndices, mcParticles, nullptr, nullptr); } } } // end loop over skimmed collisions @@ -1344,14 +1369,14 @@ struct TableMakerMC { aod::TrackAssoc const& trackAssocs, aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, tracksBarrel, tracksMuon, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, tracksBarrel, tracksMuon, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } void processPPBarrelOnly(MyEventsWithMults const& collisions, aod::BCsWithTimestamps const& bcs, MyBarrelTracksWithCov const& tracksBarrel, aod::TrackAssoc const& trackAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles, nullptr); } void processPPMuonOnlyBasic(MyEvents const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1359,7 +1384,7 @@ struct TableMakerMC { aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } void processPPMuonOnly(MyEventsWithMults const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1367,7 +1392,15 @@ struct TableMakerMC { aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); + } + + void processPPMuonRefit(MyEventsWithMults const& collisions, aod::BCsWithTimestamps const& bcs, + MyMuonsWithCov const& tracksMuon, MFTTrackLabeled const& mftTracks, + aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, + aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles, aod::MFTTracksCov const& mftCovs) + { + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, mftCovs); } void processPPRealignedMuonOnly(MyEventsWithMults const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1375,7 +1408,7 @@ struct TableMakerMC { aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } void processPbPb(MyEventsWithCentAndMults const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1383,21 +1416,21 @@ struct TableMakerMC { aod::TrackAssoc const& trackAssocs, aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, tracksBarrel, tracksMuon, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, tracksBarrel, tracksMuon, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } void processPbPbBarrelOnly(MyEventsWithCentAndMults const& collisions, aod::BCsWithTimestamps const& bcs, MyBarrelTracksWithCov const& tracksBarrel, aod::TrackAssoc const& trackAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles, nullptr); } void processPbPbWithFilterBarrelOnly(MyEventsWithMultsAndRapidityGapFilter const& collisions, aod::BCsWithTimestamps const& bcs, MyBarrelTracksWithCov const& tracksBarrel, aod::TrackAssoc const& trackAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, mcCollisions, mcParticles, nullptr); } void processPbPbMuonOnly(MyEventsWithCentAndMults const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1405,7 +1438,7 @@ struct TableMakerMC { aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } void processPbPbRealignedMuonOnly(MyEventsWithCentAndMults const& collisions, aod::BCsWithTimestamps const& bcs, @@ -1413,7 +1446,7 @@ struct TableMakerMC { aod::FwdTrackAssoc const& fwdTrackAssocs, aod::MFTTrackAssoc const& mftAssocs, aod::McCollisions const& mcCollisions, aod::McParticles const& mcParticles) { - fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles); + fullSkimming(collisions, bcs, nullptr, tracksMuon, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mcCollisions, mcParticles, nullptr); } // Process the BCs and store stats for luminosity retrieval ----------------------------------------------------------------------------------- @@ -1431,6 +1464,7 @@ struct TableMakerMC { PROCESS_SWITCH(TableMakerMC, processPPBarrelOnly, "Produce only barrel skims, pp settings ", false); PROCESS_SWITCH(TableMakerMC, processPPMuonOnlyBasic, "Produce only muon skims, pp settings, no multiplicity", false); PROCESS_SWITCH(TableMakerMC, processPPMuonOnly, "Produce only muon skims, pp settings", false); + PROCESS_SWITCH(TableMakerMC, processPPMuonRefit, "Produce only muon skims, pp settings", false); PROCESS_SWITCH(TableMakerMC, processPPRealignedMuonOnly, "Build realigned muon only DQ skimmed data model typically for pp/p-Pb and UPC Pb-Pb", false); PROCESS_SWITCH(TableMakerMC, processPbPb, "Produce both barrel and muon skims, PbPb settings", false); PROCESS_SWITCH(TableMakerMC, processPbPbBarrelOnly, "Produce only barrel skims, PbPb settings", false); diff --git a/PWGDQ/TableProducer/tableMaker_withAssoc.cxx b/PWGDQ/TableProducer/tableMaker_withAssoc.cxx index c72742c3225..97cf93bfd87 100644 --- a/PWGDQ/TableProducer/tableMaker_withAssoc.cxx +++ b/PWGDQ/TableProducer/tableMaker_withAssoc.cxx @@ -144,6 +144,7 @@ constexpr static uint32_t gkMuonRealignFillMapWithCov = VarManager::ObjTypes::Mu // constexpr static uint32_t gkMuonFillMapWithCovAmbi = VarManager::ObjTypes::Muon | VarManager::ObjTypes::MuonCov | VarManager::ObjTypes::AmbiMuon; // constexpr static uint32_t gkTrackFillMapWithAmbi = VarManager::ObjTypes::Track | VarManager::ObjTypes::AmbiTrack; constexpr static uint32_t gkMFTFillMap = VarManager::ObjTypes::TrackMFT; +constexpr static uint32_t gkMFTCovFillMap = VarManager::ObjTypes::TrackMFT | VarManager::ObjTypes::MFTCov; // Enum containing the ordering of statistics histograms to be written in the QA file enum SkimStatsHists { @@ -253,6 +254,7 @@ struct TableMaker { // Muon related options Configurable fPropMuon{"cfgPropMuon", true, "Propagate muon tracks through absorber (do not use if applying pairing)"}; Configurable fRefitGlobalMuon{"cfgRefitGlobalMuon", true, "Correct global muon parameters"}; + Configurable fKeepBestMatch{"cfgKeepBestMatch", false, "Keep only the best match global muons in the skimming"}; Configurable fMuonMatchEtaMin{"cfgMuonMatchEtaMin", -4.0f, "Definition of the acceptance of muon tracks to be matched with MFT"}; Configurable fMuonMatchEtaMax{"cfgMuonMatchEtaMax", -2.5f, "Definition of the acceptance of muon tracks to be matched with MFT"}; @@ -285,6 +287,8 @@ struct TableMaker { std::map fFwdTrackFilterMap; // key: fwd-track global index, value: fwd-track filter map std::map fMftIndexMap; // key: MFT tracklet global index, value: new MFT tracklet global index + std::map fBestMatch; + std::unordered_map map_mfttrackcovs; // FIXME: For now, the skimming is done using the Common track-collision association task, which does not allow to use // our own Filtered tracks. If the filter is very selective, then it may be worth to run the association in this workflow // using the Common/CollisionAssociation class @@ -1131,8 +1135,30 @@ struct TableMaker { } } - template - void skimMuons(TEvent const& collision, TBCs const& /*bcs*/, TMuons const& muons, FwdTrackAssoc const& muonAssocs, TMFTTracks const& /*mftTracks*/) + template + void skimBestMuonMatches(TMuons const& muons) + { + std::unordered_map> mCandidates; + for (const auto& muon : muons) { + if (static_cast(muon.trackType()) < 2) { + auto muonID = muon.matchMCHTrackId(); + auto chi2 = muon.chi2MatchMCHMFT(); + if (mCandidates.find(muonID) == mCandidates.end()) { + mCandidates[muonID] = {chi2, muon.globalIndex()}; + } else { + if (chi2 < mCandidates[muonID].first) { + mCandidates[muonID] = {chi2, muon.globalIndex()}; + } + } + } + } + for (auto& pairCand : mCandidates) { + fBestMatch[pairCand.second.second] = true; + } + } + + template + void skimMuons(TEvent const& collision, TBCs const& /*bcs*/, TMuons const& muons, FwdTrackAssoc const& muonAssocs, TMFTTracks const& /*mftTracks*/, TMFTCovs const& mfCovs) { // Skim the fwd-tracks (muons) // Loop over the collision-track associations, recompute track properties depending on the collision assigned, and apply track cuts for selection @@ -1150,6 +1176,11 @@ struct TableMaker { for (const auto& assoc : muonAssocs) { // get the muon auto muon = muons.rawIteratorAt(assoc.fwdtrackId()); + if (fConfigVariousOptions.fKeepBestMatch && static_cast(muon.trackType()) < 2) { + if (fBestMatch.find(muon.globalIndex()) == fBestMatch.end()) { + continue; + } + } trackFilteringTag = static_cast(0); trackTempFilterMap = static_cast(0); @@ -1174,11 +1205,16 @@ struct TableMaker { if (muontrack.eta() < fConfigVariousOptions.fMuonMatchEtaMin || muontrack.eta() > fConfigVariousOptions.fMuonMatchEtaMax) { continue; } + auto mfttrack = muon.template matchMFTTrack_as(); VarManager::FillTrackCollision(muontrack, collision); // NOTE: the MFT track originally associated to the MUON track is currently used in the global muon refit // Should MUON - MFT time ambiguities be taken into account ? - auto mfttrack = muon.template matchMFTTrack_as(); - VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + auto const& mfttrackcov = mfCovs.rawIteratorAt(map_mfttrackcovs[mfttrack.globalIndex()]); + VarManager::FillGlobalMuonRefitCov(muontrack, mfttrack, collision, mfttrackcov); + } else { + VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + } } else { VarManager::FillTrackCollision(muon, collision); } @@ -1265,7 +1301,12 @@ struct TableMaker { auto mfttrack = muon.template matchMFTTrack_as(); globalClusters += mfttrack.nClusters(); VarManager::FillTrackCollision(muontrack, collision); - VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + auto const& mfttrackcov = mfCovs.rawIteratorAt(map_mfttrackcovs[mfttrack.globalIndex()]); + VarManager::FillGlobalMuonRefitCov(muontrack, mfttrack, collision, mfttrackcov); + } else { + VarManager::FillGlobalMuonRefit(muontrack, mfttrack, collision); + } } else { VarManager::FillTrackCollision(muon, collision); } @@ -1289,10 +1330,10 @@ struct TableMaker { // Produce standard barrel + muon tables with event filter (typically for pp and p-Pb) ------------------------------------------------------ template + typename TTrackAssoc, typename TFwdTrackAssoc, typename TMFTTrackAssoc, typename TMFTCov> void fullSkimming(TEvents const& collisions, TBCs const& bcs, TZdcs const& zdcs, TTracks const& tracksBarrel, TMuons const& muons, TMFTTracks const& mftTracks, - TTrackAssoc const& trackAssocs, TFwdTrackAssoc const& fwdTrackAssocs, TMFTTrackAssoc const& mftAssocs) + TTrackAssoc const& trackAssocs, TFwdTrackAssoc const& fwdTrackAssocs, TMFTTrackAssoc const& mftAssocs, TMFTCov const& mftCovs) { if (bcs.size() > 0 && fCurrentRun != bcs.begin().runNumber()) { @@ -1363,6 +1404,7 @@ struct TableMaker { if constexpr (static_cast(TMFTFillMap)) { fMftIndexMap.clear(); + map_mfttrackcovs.clear(); mftTrack.reserve(mftTracks.size()); mftTrackExtra.reserve(mftTracks.size()); mftAssoc.reserve(mftTracks.size()); @@ -1371,6 +1413,7 @@ struct TableMaker { if constexpr (static_cast(TMuonFillMap)) { fFwdTrackIndexMap.clear(); fFwdTrackFilterMap.clear(); + fBestMatch.clear(); muonBasic.reserve(muons.size()); muonExtra.reserve(muons.size()); muonInfo.reserve(muons.size()); @@ -1378,6 +1421,12 @@ struct TableMaker { muonAssoc.reserve(muons.size()); } + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + for (auto& mfttrackConv : mftCovs) { + map_mfttrackcovs[mfttrackConv.matchMFTTrackId()] = mfttrackConv.globalIndex(); + } + } + // loop over selected collisions, group the compatible associations, and run the skimming for (auto const& [origIdx, skimIdx] : fCollIndexMap) { auto collision = collisions.rawIteratorAt(origIdx); @@ -1395,10 +1444,17 @@ struct TableMaker { if constexpr (static_cast(TMuonFillMap)) { if constexpr (static_cast(TMFTFillMap)) { auto groupedMuonIndices = fwdTrackAssocs.sliceBy(fwdtrackIndicesPerCollision, origIdx); - skimMuons(collision, bcs, muons, groupedMuonIndices, mftTracks); + if (fConfigVariousOptions.fKeepBestMatch) { + skimBestMuonMatches(muons); + } + if constexpr (static_cast(TMFTFillMap & VarManager::ObjTypes::MFTCov)) { + skimMuons(collision, bcs, muons, groupedMuonIndices, mftTracks, mftCovs); + } else { + skimMuons(collision, bcs, muons, groupedMuonIndices, mftTracks, nullptr); + } } else { auto groupedMuonIndices = fwdTrackAssocs.sliceBy(fwdtrackIndicesPerCollision, origIdx); - skimMuons(collision, bcs, muons, groupedMuonIndices, nullptr); + skimMuons(collision, bcs, muons, groupedMuonIndices, nullptr, nullptr); } } } // end loop over skimmed collisions @@ -1415,7 +1471,7 @@ struct TableMaker { TrackAssoc const& trackAssocs, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, tracksBarrel, muons, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, muons, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, nullptr); } // produce the barrel-only DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), subscribe to the DQ event filter (filter-pp or filter-PbPb) @@ -1423,14 +1479,14 @@ struct TableMaker { MyBarrelTracksWithCov const& tracksBarrel, TrackAssoc const& trackAssocs) { - fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the muon-only DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), subscribe to the DQ event filter (filter-pp or filter-PbPb) void processPPWithFilterMuonOnly(MyEventsWithMultsAndFilter const& collisions, BCsWithTimestamps const& bcs, MyMuonsWithCov const& muons, FwdTrackAssoc const& fwdTrackAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr, nullptr); } // produce the muon+mft DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), subscribe to the DQ event filter (filter-pp or filter-PbPb) @@ -1438,7 +1494,7 @@ struct TableMaker { MyMuonsWithCov const& muons, MFTTracks const& mftTracks, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, nullptr); } // produce the barrel-only DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), meant to run on skimmed data @@ -1446,7 +1502,7 @@ struct TableMaker { MyBarrelTracksWithCov const& tracksBarrel, TrackAssoc const& trackAssocs) { - fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the barrel-only DQ skimmed barrel data model, with V0 tagged tracks @@ -1454,21 +1510,21 @@ struct TableMaker { MyBarrelTracksWithV0BitsNoTOF const& tracksBarrel, TrackAssoc const& trackAssocs) { - fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the muon-only DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), meant to run on skimmed data void processPPMuonOnly(MyEventsWithMults const& collisions, BCsWithTimestamps const& bcs, MyMuonsWithCov const& muons, FwdTrackAssoc const& fwdTrackAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr, nullptr); } // produce the realigned muon-only DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), meant to run on skimmed data void processPPRealignedMuonOnly(MyEventsWithMults const& collisions, BCsWithTimestamps const& bcs, MyMuonsRealignWithCov const& muons, FwdTrackAssoc const& fwdTrackAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr, nullptr); } // produce the muon+mft DQ skimmed data model typically for pp/p-Pb or UPC Pb-Pb (no centrality), meant to run on skimmed data @@ -1476,7 +1532,7 @@ struct TableMaker { MyMuonsWithCov const& muons, MFTTracks const& mftTracks, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, nullptr); } // Central barrel multiplicity estimation @@ -1484,7 +1540,7 @@ struct TableMaker { MyMuonsWithCov const& muons, MFTTracks const& mftTracks, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, nullptr); } // produce the full DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter @@ -1494,7 +1550,7 @@ struct TableMaker { TrackAssoc const& trackAssocs, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, tracksBarrel, muons, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, muons, mftTracks, trackAssocs, fwdTrackAssocs, mftAssocs, nullptr); } // produce the barrel only DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter @@ -1502,7 +1558,7 @@ struct TableMaker { MyBarrelTracksWithCov const& tracksBarrel, TrackAssoc const& trackAssocs) { - fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the barrel only DQ skimmed data model typically for Pb-Pb (with centrality), no TOF @@ -1511,7 +1567,7 @@ struct TableMaker { TrackAssoc const& trackAssocs) { computeOccupancyEstimators(collisions, tracksPosWithCovNoTOF, tracksNegWithCovNoTOF, presliceWithCovNoTOF, bcs); - fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the barrel-only DQ skimmed data model typically for UPC Pb-Pb (no centrality), subscribe to the DQ rapidity gap event filter (filter-PbPb) @@ -1519,7 +1575,7 @@ struct TableMaker { MyBarrelTracksWithCov const& tracksBarrel, TrackAssoc const& trackAssocs) { - fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, zdcs, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the barrel only DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter @@ -1528,7 +1584,7 @@ struct TableMaker { TrackAssoc const& trackAssocs) { computeOccupancyEstimators(collisions, tracksPos, tracksNeg, preslice, bcs); - fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the barrel only DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter @@ -1537,21 +1593,21 @@ struct TableMaker { TrackAssoc const& trackAssocs) { computeOccupancyEstimators(collisions, tracksPosNoTOF, tracksNegNoTOF, presliceNoTOF, bcs); - fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr); + fullSkimming(collisions, bcs, nullptr, tracksBarrel, nullptr, nullptr, trackAssocs, nullptr, nullptr, nullptr); } // produce the muon only DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter void processPbPbMuonOnly(MyEventsWithCentAndMults const& collisions, BCsWithTimestamps const& bcs, MyMuonsWithCov const& muons, FwdTrackAssoc const& fwdTrackAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr, nullptr); } // produce the realigned muon only DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter void processPbPbRealignedMuonOnly(MyEventsWithCentAndMults const& collisions, BCsWithTimestamps const& bcs, MyMuonsRealignWithCov const& muons, FwdTrackAssoc const& fwdTrackAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, nullptr, nullptr, fwdTrackAssocs, nullptr, nullptr); } // produce the muon+mft DQ skimmed data model typically for Pb-Pb (with centrality), no subscribtion to the DQ event filter @@ -1559,7 +1615,16 @@ struct TableMaker { MyMuonsWithCov const& muons, MFTTracks const& mftTracks, FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs) { - fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs); + fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, nullptr); + } + + // produce the muon+mft DQ skimmed data model typically including MFT covariances + void processPPMuonRefit(MyEventsWithMults const& collisions, BCsWithTimestamps const& bcs, + MyMuonsWithCov const& muons, MFTTracks const& mftTracks, + FwdTrackAssoc const& fwdTrackAssocs, MFTTrackAssoc const& mftAssocs, + aod::MFTTracksCov const& mftCovs) + { + fullSkimming(collisions, bcs, nullptr, nullptr, muons, mftTracks, nullptr, fwdTrackAssocs, mftAssocs, mftCovs); } // Process the BCs and store stats for luminosity retrieval -----------------------------------------------------------------------------------