diff --git a/PWGLF/Tasks/phianalysis.cxx b/PWGLF/Tasks/phianalysis.cxx index f38a91eb2b1..59a86b65b2e 100644 --- a/PWGLF/Tasks/phianalysis.cxx +++ b/PWGLF/Tasks/phianalysis.cxx @@ -15,7 +15,6 @@ /// /// \author Bong-Hwi Lim -#include #include #include "Common/DataModel/PIDResponse.h" @@ -35,188 +34,273 @@ using namespace o2::soa; struct phianalysis { SliceCache cache; Preslice perRCol = aod::resodaughter::resoCollisionId; - - framework::Service ccdb; /// Accessing the CCDB - ConfigurableAxis CfgMultBins{"CfgMultBins", {VARIABLE_WIDTH, 0.0f, 20.0f, 40.0f, 60.0f, 80.0f, 100.0f, 200.0f, 99999.f}, "Mixing bins - multiplicity"}; - ConfigurableAxis CfgVtxBins{"CfgVtxBins", {VARIABLE_WIDTH, -10.0f, -8.f, -6.f, -4.f, -2.f, 0.f, 2.f, 4.f, 6.f, 8.f, 10.f}, "Mixing bins - z-vertex"}; - Configurable nEvtMixing{"nEvtMixing", 5, "Number of events to mix"}; - + Preslice perCollision = aod::track::collisionId; HistogramRegistry histos{"histos", {}, OutputObjHandlingPolicy::AnalysisObject}; - HistogramRegistry qaRegistry{"QAHistos", {}, OutputObjHandlingPolicy::QAObject}; - // Configurables - // Pre-selection cuts - Configurable cfgCutEta{"cfgCutEta", 0.8f, "Eta range for tracks"}; - Configurable mincrossedrows{"mincrossedrows", 70, "min crossed rows"}; + ///// Configurables + /// Histograms + ConfigurableAxis binsPt{"binsPt", {VARIABLE_WIDTH, 0.0, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0, 2.1, 2.2, 2.3, 2.4, 2.5, 2.6, 2.7, 2.8, 2.9, 3.0, 3.1, 3.2, 3.3, 3.4, 3.5, 3.6, 3.7, 3.8, 3.9, 4.0, 4.1, 4.2, 4.3, 4.4, 4.5, 4.6, 4.7, 4.8, 4.9, 5.0, 5.1, 5.2, 5.3, 5.4, 5.5, 5.6, 5.7, 5.8, 5.9, 6.0, 6.1, 6.2, 6.3, 6.4, 6.5, 6.6, 6.7, 6.8, 6.9, 7.0, 7.1, 7.2, 7.3, 7.4, 7.5, 7.6, 7.7, 7.8, 7.9, 8.0, 8.1, 8.2, 8.3, 8.4, 8.5, 8.6, 8.7, 8.8, 8.9, 9.0, 9.1, 9.2, 9.3, 9.4, 9.5, 9.6, 9.7, 9.8, 9.9, 10.0, 10.1, 10.2, 10.3, 10.4, 10.5, 10.6, 10.7, 10.8, 10.9, 11.0, 11.1, 11.2, 11.3, 11.4, 11.5, 11.6, 11.7, 11.8, 11.9, 12.0, 12.1, 12.2, 12.3, 12.4, 12.5, 12.6, 12.7, 12.8, 12.9, 13.0, 13.1, 13.2, 13.3, 13.4, 13.5, 13.6, 13.7, 13.8, 13.9, 14.0, 14.1, 14.2, 14.3, 14.4, 14.5, 14.6, 14.7, 14.8, 14.9, 15.0}, "Binning of the pT axis"}; + ConfigurableAxis binsPtQA{"binsPtQA", {VARIABLE_WIDTH, 0.0, 0.2, 0.4, 0.6, 0.8, 1.0, 1.2, 1.4, 1.6, 1.8, 2.0, 2.2, 2.4, 2.6, 2.8, 3.0, 3.2, 3.4, 3.6, 3.8, 4.0, 4.2, 4.4, 4.6, 4.8, 5.0, 5.2, 5.4, 5.6, 5.8, 6.0, 6.2, 6.4, 6.6, 6.8, 7.0, 7.2, 7.4, 7.6, 7.8, 8.0, 8.2, 8.4, 8.6, 8.8, 9.0, 9.2, 9.4, 9.6, 9.8, 10.0}, "Binning of the pT axis"}; + ConfigurableAxis binsCent{"binsCent", {VARIABLE_WIDTH, 0., 1., 5., 10., 30., 50., 70., 100., 105.}, "Binning of the centrality axis"}; + Configurable cInvMassStart{"cInvMassStart", 0.6, "Invariant mass start"}; + Configurable cInvMassEnd{"cInvMassEnd", 1.5, "Invariant mass end"}; + Configurable cInvMassBins{"cInvMassBins", 900, "Invariant mass binning"}; + Configurable cPIDBins{"cPIDBins", 65, "PID binning"}; + Configurable cPIDQALimit{"cPIDQALimit", 6.5, "PID QA limit"}; + Configurable cDCABins{"cDCABins", 150, "DCA binning"}; + /// Event Mixing + Configurable nEvtMixing{"nEvtMixing", 5, "Number of events to mix"}; + ConfigurableAxis CfgVtxBins{"CfgVtxBins", {VARIABLE_WIDTH, -10.0f, -8.f, -6.f, -4.f, -2.f, 0.f, 2.f, 4.f, 6.f, 8.f, 10.f}, "Mixing bins - z-vertex"}; + ConfigurableAxis CfgMultBins{"CfgMultBins", {VARIABLE_WIDTH, 0., 1., 5., 10., 30., 50., 70., 100., 105.}, "Mixing bins - multiplicity"}; + /// Pre-selection cuts Configurable cMinPtcut{"cMinPtcut", 0.15, "Track minium pt cut"}; - /// DCA Selections // DCAr to PV Configurable cMaxDCArToPVcut{"cMaxDCArToPVcut", 0.5, "Track DCAr cut to PV Maximum"}; // DCAz to PV Configurable cMaxDCAzToPVcut{"cMaxDCAzToPVcut", 2.0, "Track DCAz cut to PV Maximum"}; Configurable cMinDCAzToPVcut{"cMinDCAzToPVcut", 0.0, "Track DCAz cut to PV Minimum"}; - - Preslice perCollision = aod::track::collisionId; + /// PID Selections + Configurable cMaxTPCnSigmaPion{"cMaxTPCnSigmaPion", 3.0, "TPC nSigma cut for Pion"}; // TPC + Configurable nsigmaCutCombinedPion{"nsigmaCutCombinedPion", 3.0, "Combined nSigma cut for Pion"}; // Combined + // Kaon + Configurable cMaxTPCnSigmaKaon{"cMaxTPCnSigmaKaon", 3.0, "TPC nSigma cut for Kaon"}; // TPC + Configurable nsigmaCutCombinedKaon{"nsigmaCutCombinedKaon", 3.0, "Combined nSigma cut for Kaon"}; // Combined + // Track selections + Configurable cfgPrimaryTrack{"cfgPrimaryTrack", true, "Primary track selection"}; // kGoldenChi2 | kDCAxy | kDCAz + Configurable cfgGlobalWoDCATrack{"cfgGlobalWoDCATrack", true, "Global track selection without DCA"}; // kQualityTracks (kTrackType | kTPCNCls | kTPCCrossedRows | kTPCCrossedRowsOverNCls | kTPCChi2NDF | kTPCRefit | kITSNCls | kITSChi2NDF | kITSRefit | kITSHits) | kInAcceptanceTracks (kPtRange | kEtaRange) + Configurable cfgPVContributor{"cfgPVContributor", true, "PV contributor track selection"}; // PV Contriuibutor void init(o2::framework::InitContext&) { - ccdb->setURL("http://alice-ccdb.cern.ch"); - ccdb->setCaching(true); - ccdb->setLocalObjectValidityChecking(); - uint64_t now = std::chrono::duration_cast(std::chrono::system_clock::now().time_since_epoch()).count(); - ccdb->setCreatedNotAfter(now); - - AxisSpec vtxZAxis = {100, -20, 20}; - - std::vector centBinning = {0., 1., 5., 10., 20., 30., 40., 50., 70., 100.}; - AxisSpec centAxis = {centBinning, "V0M (%)"}; - std::vector ptBinning = {0.5, 0.6, 0.7, 0.8, 0.9, 1.0, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.8, 2.0, 2.2, 2.4, 2.8, 3.2, 3.6, 4., 5., 10., 20.}; - AxisSpec ptAxis = {ptBinning, "#it{p}_{T} (GeV/#it{c})"}; + AxisSpec centAxis = {binsCent, "V0M (%)"}; + AxisSpec dcaxyAxis = {cDCABins, 0.0, 3.0, "DCA_{#it{xy}} (cm)"}; + AxisSpec dcazAxis = {cDCABins, 0.0, 3.0, "DCA_{#it{xy}} (cm)"}; + AxisSpec ptAxis = {binsPt, "#it{p}_{T} (GeV/#it{c})"}; + AxisSpec ptAxisQA = {binsPtQA, "#it{p}_{T} (GeV/#it{c})"}; + AxisSpec invMassAxis = {cInvMassBins, cInvMassStart, cInvMassEnd, "Invariant Mass (GeV/#it{c}^2)"}; + AxisSpec pidQAAxis = {cPIDBins, -cPIDQALimit, cPIDQALimit}; // Mass QA (quick check) - histos.add("phiinvmass", "Invariant mass of Phi", kTH1F, {{700, 0.8, 1.5, "Invariant Mass (GeV/#it{c}^2)"}}); - histos.add("phiinvmassME", "Invariant mass of Phi mixed event", kTH1F, {{700, 0.8, 1.5, "Invariant Mass (GeV/#it{c}^2)"}}); - histos.add("trk1pT", "pT distribution of track1", kTH1F, {{100, 0, 10, "#it{p}_{T} (GeV/#it{c})"}}); - histos.add("trk2pT", "pT distribution of track1", kTH1F, {{100, 0, 10, "#it{p}_{T} (GeV/#it{c})"}}); - histos.add("TOF_TPC_Map1", "TOF + TPC Combined PID for Kaons;#sigma_{TOF}^{Kaon};#sigma_{TPC}^{Kaon}", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); - histos.add("TOF_Nsigma1", "TOF NSigma for Kaons;#it{p}_{T} (GeV/#it{c});#sigma_{TOF}^{Kaon};", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); - histos.add("TPC_Nsigma1", "TPC NSigma for Kaons;#it{p}_{T} (GeV/#it{c});#sigma_{TPC}^{Kaon};", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); - histos.add("TOF_TPC_Map2", "TOF + TPC Combined PID for Kaons;#sigma_{TOF}^{Kaon};#sigma_{TPC}^{Kaon}", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); - histos.add("TOF_Nsigma2", "TOF NSigma for Kaons;#it{p}_{T} (GeV/#it{c});#sigma_{TOF}^{Kaon};", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); - histos.add("TPC_Nsigma2", "TPC NSigma for Kaons;#it{p}_{T} (GeV/#it{c});#sigma_{TPC}^{Kaon};", {HistType::kTH2F, {{200, -10, 10}, {200, -10, 10}}}); + histos.add("phiinvmassDS", "Invariant mass of phi differnt sign", kTH1F, {invMassAxis}); + histos.add("phiinvmassLS", "Invariant mass of phi like sign", kTH1F, {invMassAxis}); + histos.add("phiinvmassME", "Invariant mass of phi mixed event", kTH1F, {invMassAxis}); + // DCA QA + histos.add("QAbefore/trkDCAxy", "DCAxy distribution of kaon track candidates", HistType::kTH1F, {dcaxyAxis}); + histos.add("QAbefore/trkDCAz", "DCAz distribution of kaon track candidates", HistType::kTH1F, {dcazAxis}); + histos.add("QAafter/trkDCAxy", "DCAxy distribution of kaon track candidates", HistType::kTH1F, {dcaxyAxis}); + histos.add("QAafter/trkDCAz", "DCAz distribution of kaon track candidates", HistType::kTH1F, {dcazAxis}); + // pT QA + histos.add("QAbefore/trkpT", "pT distribution of kaon track candidates", kTH1F, {ptAxis}); + histos.add("QAafter/trkpT", "pT distribution of kaon track candidates", kTH1F, {ptAxis}); + // PID QA before cuts + histos.add("QAbefore/TOF_TPC_Mapka_all", "TOF + TPC Combined PID for Pion;#sigma_{TOF}^{Kaon};#sigma_{TPC}^{Kaon}", {HistType::kTH2D, {pidQAAxis, pidQAAxis}}); + histos.add("QAbefore/TOF_Nsigma_all", "TOF NSigma for Pion;#it{p}_{T} (GeV/#it{c});#sigma_{TOF}^{Kaon};", {HistType::kTH2D, {ptAxisQA, pidQAAxis}}); + histos.add("QAbefore/TPC_Nsigmaka_all", "TPC NSigma for Kaon;#it{p}_{T} (GeV/#it{c});#sigma_{TPC}^{Kaon};", {HistType::kTH2D, {ptAxisQA, pidQAAxis}}); + // PID QA after cuts + histos.add("QAafter/TOF_TPC_Mapka_all", "TOF + TPC Combined PID for Pion;#sigma_{TOF}^{Kaon};#sigma_{TPC}^{Kaon}", {HistType::kTH2D, {pidQAAxis, pidQAAxis}}); + histos.add("QAafter/TOF_Nsigma_all", "TOF NSigma for Pion;#it{p}_{T} (GeV/#it{c});#sigma_{TOF}^{Kaon};", {HistType::kTH2D, {ptAxisQA, pidQAAxis}}); + histos.add("QAafter/TPC_Nsigmaka_all", "TPC NSigma for Kaon;#it{p}_{T} (GeV/#it{c});#sigma_{TPC}^{Kaon};", {HistType::kTH2D, {ptAxisQA, pidQAAxis}}); // 3d histogram - histos.add("h3phiinvmass", "Invariant mass of Phi", kTH3F, {{300, 0, 3000}, {100, 0.0f, 10.0f}, {700, 0.8, 1.5}}); - histos.add("h3phiinvmassME", "Invariant mass of Phi mixed event", kTH3F, {{300, 0, 3000}, {100, 0.0f, 10.0f}, {700, 0.8, 1.5}}); - - if (doprocessMC) { - histos.add("h3recophiinvmass", "Invariant mass of Reconstructed MC Phi", kTH3F, {{300, 0, 3000}, {100, 0.0f, 10.0f}, {700, 0.8, 1.5}}); - histos.add("truephipt", "pT distribution of True MC Phi", kTH1F, {{100, 0, 10, "#it{p}_{T} (GeV/#it{c})"}}); - histos.add("reconphipt", "pT distribution of Reconstructed MC Phi", kTH1F, {{100, 0, 10, "#it{p}_{T} (GeV/#it{c})"}}); - histos.add("reconphiinvmass", "Inv mass distribution of Reconstructed MC Phi", kTH1F, {{700, 0.8, 1.5, "Invariant Mass (GeV/#it{c}^2)"}}); + histos.add("h3phiinvmassDS", "Invariant mass of phi differnt sign", kTH3F, {centAxis, ptAxis, invMassAxis}); + histos.add("h3phiinvmassLS", "Invariant mass of phi same sign", kTH3F, {centAxis, ptAxis, invMassAxis}); + histos.add("h3phiinvmassME", "Invariant mass of phi mixed event", kTH3F, {centAxis, ptAxis, invMassAxis}); + + if (doprocessMCLight) { + // MC QA + histos.add("QAMCTrue/trkDCAxy", "DCAxy distribution of kaon track candidates", HistType::kTH1F, {dcaxyAxis}); + histos.add("QAMCTrue/trkDCAz", "DCAz distribution of kaon track candidates", HistType::kTH1F, {dcazAxis}); + histos.add("h3Recphiinvmass", "Invariant mass of Reconstructed MC phi", kTH3F, {centAxis, ptAxis, invMassAxis}); + histos.add("phiGen", "pT distribution of True MC phi", kTH1F, {ptAxis}); + histos.add("phiRec", "pT distribution of Reconstructed MC phi", kTH1F, {ptAxis}); + histos.add("phiRecinvmass", "Inv mass distribution of Reconstructed MC Phi", kTH1F, {invMassAxis}); } + // Print output histograms statistics + LOG(info) << "Size of the histograms in phi analysis:"; + histos.print(); } double massKa = TDatabasePDG::Instance()->GetParticle(kKPlus)->Mass(); - template - void fillHistograms(const CollisionType& collision, const TracksType& dTracks) + template + bool trackCut(const TrackType track) + { + // basic track cuts + if (std::abs(track.pt()) < cMinPtcut) + return false; + if (std::abs(track.dcaXY()) > cMaxDCArToPVcut) + return false; + if (std::abs(track.dcaZ()) > cMaxDCAzToPVcut) + return false; + if (cfgPrimaryTrack && !track.isPrimaryTrack()) + return false; + if (cfgGlobalWoDCATrack && !track.isGlobalTrackWoDCA()) + return false; + if (cfgPVContributor && !track.isPVContributor()) + return false; + + return true; + } + // PID selection tools from phianalysisrun3 + template + bool selectionPIDKaon(const T& candidate, bool hasTOF) + { + if (hasTOF && (candidate.tofNSigmaKa() * candidate.tofNSigmaKa() + candidate.tpcNSigmaKa() * candidate.tpcNSigmaKa()) < (2.0 * nsigmaCutCombinedKaon * nsigmaCutCombinedKaon)) { + return true; + } else if (std::abs(candidate.tpcNSigmaKa()) < cMaxTPCnSigmaKaon) { + return true; + } + return false; + } + + template + void fillHistograms(const CollisionType& collision, const TracksType& dTracks1, const TracksType& dTracks2) { TLorentzVector lDecayDaughter1, lDecayDaughter2, lResonance; - for (auto& [trk1, trk2] : combinations(CombinationsUpperIndexPolicy(dTracks, dTracks))) { - // Un-like sign pair only - if (trk1.sign() * trk2.sign() > 0) + for (auto& [trk1, trk2] : combinations(CombinationsFullIndexPolicy(dTracks1, dTracks2))) { + // Full index policy is needed to consider all possible combinations + if (trk1.index() == trk2.index()) + continue; // We need to run (0,1), (1,0) pairs as well. but same id pairs are not needed. + //// Initialize variables + // Trk1: Kaon, Trk2: Kaon + // apply the track cut + if (!trackCut(trk1) || !trackCut(trk2)) continue; - // pT-dependent TPC PID cut - if ((trk1.pt() < 0.3) && (std::abs(trk1.tpcNSigmaKa()) > 6.0)) - continue; - if ((trk1.pt() >= 0.3) && (trk1.pt() < 0.4) && (std::abs(trk1.tpcNSigmaKa()) > 4.0)) - continue; - if ((trk1.pt() >= 0.4) && (std::abs(trk1.tpcNSigmaKa()) > 2.0)) - continue; + auto isTrk1hasTOF = ((trk1.tofPIDselectionFlag() & aod::resodaughter::kHasTOF) == aod::resodaughter::kHasTOF) ? true : false; + auto isTrk2hasTOF = ((trk2.tofPIDselectionFlag() & aod::resodaughter::kHasTOF) == aod::resodaughter::kHasTOF) ? true : false; + auto trk1ptKa = trk1.pt(); + auto trk1NSigmaKaTPC = trk1.tpcNSigmaKa(); + auto trk1NSigmaKaTOF = (isTrk1hasTOF) ? trk1.tofNSigmaPi() : -999.; + // auto trk2ptKa = trk2.pt(); + // auto trk2NSigmaKaTPC = trk2.tpcNSigmaKa(); + // auto trk2NSigmaKaTOF = (isTrk2hasTOF) ? trk2.tofNSigmaKa() : -999.; - if ((trk2.pt() < 0.3) && (std::abs(trk2.tpcNSigmaKa()) > 6.0)) - continue; - if ((trk2.pt() >= 0.3) && (trk2.pt() < 0.4) && (std::abs(trk2.tpcNSigmaKa()) > 4.0)) - continue; - if ((trk2.pt() >= 0.4) && (std::abs(trk2.tpcNSigmaKa()) > 2.0)) + if constexpr (!IsMix) { + //// QA plots before the selection + // --- PID QA Kaon + histos.fill(HIST("QAbefore/TPC_Nsigmaka_all"), trk1ptKa, trk1NSigmaKaTPC); + if (isTrk1hasTOF) { + histos.fill(HIST("QAbefore/TOF_Nsigma_all"), trk1ptKa, trk1NSigmaKaTOF); + histos.fill(HIST("QAbefore/TOF_TPC_Mapka_all"), trk1NSigmaKaTOF, trk1NSigmaKaTPC); + } + histos.fill(HIST("QAbefore/trkpT"), trk1ptKa); + histos.fill(HIST("QAbefore/trkDCAxy"), trk1.dcaXY()); + histos.fill(HIST("QAbefore/trkDCAz"), trk1.dcaZ()); + } + + //// Apply the selection + if (!selectionPIDKaon(trk1, isTrk1hasTOF) || !selectionPIDKaon(trk2, isTrk2hasTOF)) continue; - if (trk1.sign() > 0) { - // --- PID QA Kaons + - histos.fill(HIST("TOF_Nsigma1"), trk1.pt(), trk1.tofNSigmaKa()); - histos.fill(HIST("TPC_Nsigma1"), trk1.pt(), trk1.tpcNSigmaKa()); - histos.fill(HIST("TOF_TPC_Map1"), trk1.tofNSigmaKa(), trk1.tpcNSigmaKa()); - // --- PID QA Kaons - - histos.fill(HIST("TOF_Nsigma2"), trk2.pt(), trk2.tofNSigmaKa()); - histos.fill(HIST("TPC_Nsigma2"), trk2.pt(), trk2.tpcNSigmaKa()); - histos.fill(HIST("TOF_TPC_Map2"), trk2.tofNSigmaKa(), trk2.tpcNSigmaKa()); - } else { - // --- PID QA Kaons + - histos.fill(HIST("TOF_Nsigma1"), trk2.pt(), trk2.tofNSigmaKa()); - histos.fill(HIST("TPC_Nsigma1"), trk2.pt(), trk2.tpcNSigmaKa()); - histos.fill(HIST("TOF_TPC_Map1"), trk2.tofNSigmaKa(), trk2.tpcNSigmaKa()); - // --- PID QA Kaons - - histos.fill(HIST("TOF_Nsigma2"), trk1.pt(), trk1.tofNSigmaKa()); - histos.fill(HIST("TPC_Nsigma2"), trk1.pt(), trk1.tpcNSigmaKa()); - histos.fill(HIST("TOF_TPC_Map2"), trk1.tofNSigmaKa(), trk1.tpcNSigmaKa()); + if constexpr (!IsMix) { + //// QA plots after the selection + // --- PID QA Kaon + histos.fill(HIST("QAafter/TPC_Nsigmaka_all"), trk1ptKa, trk1NSigmaKaTPC); + if (isTrk1hasTOF) { + histos.fill(HIST("QAafter/TOF_Nsigma_all"), trk1ptKa, trk1NSigmaKaTOF); + histos.fill(HIST("QAafter/TOF_TPC_Mapka_all"), trk1NSigmaKaTOF, trk1NSigmaKaTPC); + } + histos.fill(HIST("QAafter/trkpT"), trk1ptKa); + histos.fill(HIST("QAafter/trkDCAxy"), trk1.dcaXY()); + histos.fill(HIST("QAafter/trkDCAz"), trk1.dcaZ()); } - histos.fill(HIST("trk1pT"), trk1.pt()); - histos.fill(HIST("trk2pT"), trk2.pt()); - + //// Resonance reconstruction lDecayDaughter1.SetXYZM(trk1.px(), trk1.py(), trk1.pz(), massKa); lDecayDaughter2.SetXYZM(trk2.px(), trk2.py(), trk2.pz(), massKa); lResonance = lDecayDaughter1 + lDecayDaughter2; - - if (lResonance.Rapidity() > 0.5 || lResonance.Rapidity() < -0.5) + // Rapidity cut + if (abs(lResonance.Rapidity()) > 0.5) continue; + //// Un-like sign pair only + if (trk1.sign() * trk2.sign() < 0) { + if constexpr (!IsMix) { + if (trk1.sign() > 0) { + histos.fill(HIST("phiinvmassDS"), lResonance.M()); + histos.fill(HIST("h3phiinvmassDS"), collision.multV0M(), lResonance.Pt(), lResonance.M()); + } else { + } + } else { + histos.fill(HIST("phiinvmassME"), lResonance.M()); + histos.fill(HIST("h3phiinvmassME"), collision.multV0M(), lResonance.Pt(), lResonance.M()); + } + + // MC + if constexpr (IsMC) { + if (abs(trk1.pdgCode()) != kKPlus || abs(trk2.pdgCode()) != kKPlus) + continue; + if (trk1.motherId() != trk2.motherId()) // Same mother + continue; + if (abs(trk1.motherPDG()) != 333) + continue; - histos.fill(HIST("phiinvmass"), lResonance.M()); - histos.fill(HIST("h3phiinvmass"), collision.multV0M(), lResonance.Pt(), lResonance.M()); + // Track selection check. + histos.fill(HIST("QAMCTrue/trkDCAxy"), trk2.dcaXY()); + histos.fill(HIST("QAMCTrue/trkDCAz"), trk2.dcaZ()); - if constexpr (IsMC) { - if (abs(trk1.pdgCode()) != kKPlus || abs(trk2.pdgCode()) != kKPlus) // check if the tracks are kaons + // MC histograms + histos.fill(HIST("phiRec"), lResonance.Pt()); + histos.fill(HIST("phiRecinvmass"), lResonance.M()); + histos.fill(HIST("h3Recphiinvmass"), collision.multV0M(), lResonance.Pt(), lResonance.M()); + } + } else { + if constexpr (!IsMix) continue; - auto mother1 = trk1.motherId(); - auto mother2 = trk2.motherId(); - if (mother1 == mother2) { // Same mother - if (trk1.motherPDG() == 333) { // Phi - histos.fill(HIST("reconphiinvmass"), lResonance.M()); - histos.fill(HIST("reconphipt"), lResonance.Pt()); - histos.fill(HIST("h3recophiinvmass"), collision.multV0M(), lResonance.Pt(), lResonance.M()); - } + if (trk1.sign() > 0) { + histos.fill(HIST("phiinvmassLS"), lResonance.M()); + histos.fill(HIST("h3phiinvmassLS"), collision.multV0M(), lResonance.Pt(), lResonance.M()); + } else { } } } } - void processData(aod::ResoCollisions& collisions, - aod::ResoTracks const& resotracks) + void processDataLight(aod::ResoCollision& collision, + aod::ResoTracks const& resotracks) { - LOGF(debug, "[DATA] Processing %d collisions", collisions.size()); - for (auto& collision : collisions) { - Partition selectedTracks = requireTOFPIDKaonCutInFilter() && (o2::aod::track::pt > static_cast(cMinPtcut)) && (nabs(o2::aod::track::dcaZ) > static_cast(cMinDCAzToPVcut)) && (nabs(o2::aod::track::dcaZ) < static_cast(cMaxDCAzToPVcut)) && (nabs(o2::aod::track::dcaXY) < static_cast(cMaxDCArToPVcut)); // Basic DCA cuts - selectedTracks.bindTable(resotracks); - auto colTracks = selectedTracks->sliceByCached(aod::resodaughter::resoCollisionId, collision.globalIndex(), cache); - fillHistograms(collision, colTracks); - } + // LOG(info) << "new collision, zvtx: " << collision.posZ(); + fillHistograms(collision, resotracks, resotracks); } - PROCESS_SWITCH(phianalysis, processData, "Process Event for data", true); + PROCESS_SWITCH(phianalysis, processDataLight, "Process Event for data", false); - void processMC(aod::ResoCollisions& collisions, - soa::Join const& resotracks, aod::McParticles const& mcParticles) + void processMCLight(aod::ResoCollision& collision, + soa::Join const& resotracks, aod::McParticles const& mcParticles) { - LOGF(debug, "[MC] MC events: %d", collisions.size()); - for (auto& collision : collisions) { - Partition> selectedTracks = requireTOFPIDKaonCutInFilter() && (o2::aod::track::pt > static_cast(cMinPtcut)) && (nabs(o2::aod::track::dcaZ) > static_cast(cMinDCAzToPVcut)) && (nabs(o2::aod::track::dcaZ) < static_cast(cMaxDCAzToPVcut)) && (nabs(o2::aod::track::dcaXY) < static_cast(cMaxDCArToPVcut)); // Basic DCA cuts - selectedTracks.bindTable(resotracks); - auto colTracks = selectedTracks->sliceByCached(aod::resodaughter::resoCollisionId, collision.globalIndex(), cache); - fillHistograms(collision, colTracks); - } + fillHistograms(collision, resotracks, resotracks); + } + PROCESS_SWITCH(phianalysis, processMCLight, "Process Event for MC", false); - // Not related to the real collisions - for (auto& part : mcParticles) { // loop over all MC particles - if (abs(part.pdgCode()) == 333) { // Phi - if (part.y() > 0.5 || part.y() < -0.5) { // rapidity cut - continue; - } - bool isDecaytoKaons = true; - for (auto& dau : part.daughters_as()) { - if (abs(dau.pdgCode()) != kKPlus) { // Decay to Kaons - isDecaytoKaons = false; - break; - } - } - if (!isDecaytoKaons) - continue; - histos.fill(HIST("truephipt"), part.pt()); + void processMCTrue(aod::ResoMCParents& resoParents) + { + for (auto& part : resoParents) { // loop over all pre-filtered MC particles + if (abs(part.pdgCode()) != 333) // phi(0) + continue; + if (abs(part.y()) > 0.5) { // rapidity cut + continue; } + if (abs(part.daughterPDG1()) != kKPlus || abs(part.daughterPDG2()) != kKPlus) { // At least one decay to Kaon + continue; + } + histos.fill(HIST("phiGen"), part.pt()); } } - PROCESS_SWITCH(phianalysis, processMC, "Process Event for MC", false); + PROCESS_SWITCH(phianalysis, processMCTrue, "Process Event for MC", false); + + // Processing Event Mixing + using BinningTypeVtxZT0M = ColumnBinningPolicy; + BinningTypeVtxZT0M colBinning{{CfgVtxBins, CfgMultBins}, true}; + void processMELight(o2::aod::ResoCollisions& collisions, aod::ResoTracks const& resotracks) + { + auto tracksTuple = std::make_tuple(resotracks); + SameKindPair pairs{colBinning, nEvtMixing, -1, collisions, tracksTuple, &cache}; // -1 is the number of the bin to skip + + for (auto& [collision1, tracks1, collision2, tracks2] : pairs) { + fillHistograms(collision1, tracks1, tracks2); + } + }; + PROCESS_SWITCH(phianalysis, processMELight, "Process EventMixing light without partition", false); }; WorkflowSpec defineDataProcessing(ConfigContext const& cfgc)