@@ -109,6 +109,7 @@ struct lambdapolsp {
109109 Configurable<double > etaMix{" etaMix" , 0.1 , " eta difference in mixing" };
110110 Configurable<double > ptMix{" ptMix" , 0.1 , " pt difference in mixing" };
111111 Configurable<double > phiMix{" phiMix" , 0.1 , " phi difference in mixing" };
112+ Configurable<bool > useSP{" useSP" , false , " use scalar product" };
112113 } randGrp;
113114 // events
114115 Configurable<float > cfgCutVertex{" cfgCutVertex" , 10 .0f , " Accepted z-vertex range" };
@@ -232,6 +233,7 @@ struct lambdapolsp {
232233 std::vector<AxisSpec> runaxes = {thnAxisInvMass, axisGrp.configthnAxispT , axisGrp.configthnAxisPol , axisGrp.configcentAxis };
233234 if (needetaaxis)
234235 runaxes.insert (runaxes.end (), {axisGrp.configbinAxis });
236+ std::vector<AxisSpec> runaxes2 = {thnAxisInvMass, axisGrp.configthnAxispT , axisGrp.configcentAxis };
235237
236238 if (checkwithpub) {
237239 if (useprofile == 2 ) {
@@ -428,6 +430,11 @@ struct lambdapolsp {
428430 histos.add (" hptnegantilambda" , " hptnegantilambda" , HistType::kTH1D , {distGrp.axispt }, true );
429431 }
430432
433+ histos.add (" hSparseGenLambda" , " hSparseGenLambda" , HistType::kTHnSparseF , runaxes2, true );
434+ histos.add (" hSparseGenAntiLambda" , " hSparseGenAntiLambda" , HistType::kTHnSparseF , runaxes2, true );
435+ histos.add (" hSparseRecLambda" , " hSparseRecLambda" , HistType::kTHnSparseF , runaxes2, true );
436+ histos.add (" hSparseRecAntiLambda" , " hSparseRecAntiLambda" , HistType::kTHnSparseF , runaxes2, true );
437+
431438 ccdb->setURL (cfgCcdbParam.cfgURL );
432439 ccdbApi.init (" http://alice-ccdb.cern.ch" );
433440 ccdb->setCaching (true );
@@ -672,6 +679,10 @@ struct lambdapolsp {
672679 if (randGrp.doRandomPhi ) {
673680 phiangle = randPhi.Uniform (0 , 2 * TMath::Pi ());
674681 }
682+
683+ auto ux = TMath::Cos (phiangle);
684+ auto uy = TMath::Sin (phiangle);
685+
675686 auto phiminuspsiC = GetPhiInRange (phiangle - psiZDCC);
676687 auto phiminuspsiA = GetPhiInRange (phiangle - psiZDCA);
677688 auto phiminuspsi = GetPhiInRange (phiangle - psiZDC);
@@ -680,6 +691,7 @@ struct lambdapolsp {
680691 auto PolC = TMath::Sin (phiminuspsiC);
681692 auto PolA = TMath::Sin (phiminuspsiA);
682693 auto Pol = TMath::Sin (phiminuspsi);
694+ auto PolSP = uy * TMath::Cos (psiZDC) - ux * TMath::Sin (psiZDC);
683695
684696 auto sinPhiStar = TMath::Sin (GetPhiInRange (phiangle));
685697 auto cosPhiStar = TMath::Cos (GetPhiInRange (phiangle));
@@ -694,6 +706,9 @@ struct lambdapolsp {
694706 auto PolAwgt = PolA / acvalue;
695707 auto PolCwgt = PolC / acvalue;
696708
709+ if (randGrp.useSP )
710+ Polwgt = PolSP / acvalue;
711+
697712 // Fill histograms using constructed names
698713 if (tag2) {
699714 if (needetaaxis) {
@@ -807,6 +822,7 @@ struct lambdapolsp {
807822 Filter dcaCutFilter = (nabs(aod::track::dcaXY) < cfgCutDCAxy) && (nabs(aod::track::dcaZ) < cfgCutDCAz);
808823
809824 using EventCandidates = soa::Filtered<soa::Join<aod::Collisions, aod::EvSels, aod::FT0Mults, aod::FV0Mults, aod::TPCMults, aod::CentFV0As, aod::CentFT0Ms, aod::CentFT0Cs, aod::CentFT0As, aod::SPCalibrationTables, aod::Mults>>;
825+ using EventCandidatesMC = soa::Filtered<soa::Join<aod::Collisions, aod::EvSels, aod::CentFT0Cs>>;
810826 using AllTrackCandidates = soa::Filtered<soa::Join<aod::Tracks, aod::TracksExtra, aod::TracksDCA, aod::TrackSelection, aod::pidTPCFullPi, aod::pidTPCFullPr, aod::pidTPCFullKa>>;
811827 using ResoV0s = aod::V0Datas;
812828
@@ -895,6 +911,8 @@ struct lambdapolsp {
895911 if (!checkwithpub) {
896912 // histos.fill(HIST("hVtxZ"), collision.posZ());
897913 histos.fill (HIST (" hpRes" ), centrality, (TMath::Cos (GetPhiInRange (psiZDCA - psiZDCC))));
914+ if (randGrp.useSP )
915+ histos.fill (HIST (" hpRes" ), centrality, ((modqxZDCA * modqxZDCC) + (modqyZDCA * modqyZDCC)));
898916 // histos.fill(HIST("hpResSin"), centrality, (TMath::Sin(GetPhiInRange(psiZDCA - psiZDCC))));
899917 /* histos.fill(HIST("hpCosPsiA"), centrality, (TMath::Cos(GetPhiInRange(psiZDCA))));
900918 histos.fill(HIST("hpCosPsiC"), centrality, (TMath::Cos(GetPhiInRange(psiZDCC))));
@@ -1505,7 +1523,142 @@ struct lambdapolsp {
15051523 }
15061524 PROCESS_SWITCH (lambdapolsp, processDerivedData, " Process derived data" , false );
15071525
1526+ using TrackMCTrueTable = aod::McParticles;
1527+ ROOT::Math::PxPyPzMVector lambdamc, antiLambdamc, lambdadummymc, antiLambdadummymc, protonmc, pionmc, antiProtonmc, antiPionmc;
1528+
1529+ void processMC (EventCandidatesMC::iterator const & collision, AllTrackCandidates const & tracks, TrackMCTrueTable const & GenParticles, ResoV0s const & V0s)
1530+ {
1531+ if (!collision.sel8 ()) {
1532+ return ;
1533+ }
1534+ double centrality = -999 .;
1535+ centrality = collision.centFT0C ();
1536+
1537+ if (additionalEvSel && (!collision.selection_bit (aod::evsel::kNoSameBunchPileup ) || !collision.selection_bit (aod::evsel::kIsGoodZvtxFT0vsPV ))) {
1538+ return ;
1539+ }
1540+
1541+ if (additionalEvSel2 && (collision.trackOccupancyInTimeRange () > cfgMaxOccupancy || collision.trackOccupancyInTimeRange () < cfgMinOccupancy)) {
1542+ return ;
1543+ }
1544+
1545+ if (additionalEvSel3 && (!collision.selection_bit (aod::evsel::kNoTimeFrameBorder ) || !collision.selection_bit (aod::evsel::kNoITSROFrameBorder ))) {
1546+ return ;
1547+ }
1548+ if (additionalEvSel4 && !collision.selection_bit (o2::aod::evsel::kIsGoodITSLayersAll )) {
1549+ return ;
1550+ }
1551+
1552+ if (rctCut.requireRCTFlagChecker && !rctChecker (collision)) {
1553+ return ;
1554+ }
1555+
1556+ histos.fill (HIST (" hCentrality" ), centrality);
1557+
1558+ for (const auto & v0 : V0s) {
1559+
1560+ auto postrack = v0.template posTrack_as <AllTrackCandidates>();
1561+ auto negtrack = v0.template negTrack_as <AllTrackCandidates>();
1562+
1563+ int LambdaTag = 0 ;
1564+ int aLambdaTag = 0 ;
1565+
1566+ const auto signpos = postrack.sign ();
1567+ const auto signneg = negtrack.sign ();
1568+
1569+ if (signpos < 0 || signneg > 0 ) {
1570+ continue ;
1571+ }
1572+
1573+ if (isSelectedV0Daughter (v0, postrack, 0 , 0 ) && isSelectedV0Daughter (v0, negtrack, 1 , 0 )) {
1574+ LambdaTag = 1 ;
1575+ }
1576+ if (isSelectedV0Daughter (v0, negtrack, 0 , 1 ) && isSelectedV0Daughter (v0, postrack, 1 , 1 )) {
1577+ aLambdaTag = 1 ;
1578+ }
1579+
1580+ if (!LambdaTag && !aLambdaTag)
1581+ continue ;
1582+
1583+ if (!SelectionV0 (collision, v0)) {
1584+ continue ;
1585+ }
1586+
1587+ if (LambdaTag) {
1588+ Proton = ROOT::Math::PxPyPzMVector (v0.pxpos (), v0.pypos (), v0.pzpos (), massPr);
1589+ AntiPion = ROOT::Math::PxPyPzMVector (v0.pxneg (), v0.pyneg (), v0.pzneg (), massPi);
1590+ Lambdadummy = Proton + AntiPion;
1591+ }
1592+ if (aLambdaTag) {
1593+ AntiProton = ROOT::Math::PxPyPzMVector (v0.pxneg (), v0.pyneg (), v0.pzneg (), massPr);
1594+ Pion = ROOT::Math::PxPyPzMVector (v0.pxpos (), v0.pypos (), v0.pzpos (), massPi);
1595+ AntiLambdadummy = AntiProton + Pion;
1596+ }
1597+
1598+ if (shouldReject (LambdaTag, aLambdaTag, Lambdadummy, AntiLambdadummy)) {
1599+ continue ;
1600+ }
1601+
1602+ if (TMath::Abs (v0.eta ()) > 0.8 )
1603+ continue ;
1604+
1605+ if (LambdaTag) {
1606+ Lambda = Proton + AntiPion;
1607+ histos.fill (HIST (" hSparseRecLambda" ), v0.mLambda (), v0.pt (), centrality);
1608+ }
1609+ if (aLambdaTag) {
1610+ AntiLambda = AntiProton + Pion;
1611+ histos.fill (HIST (" hSparseRecAntiLambda" ), v0.mAntiLambda (), v0.pt (), centrality);
1612+ }
1613+ }
1614+
1615+ for (const auto & mcParticle : GenParticles) {
1616+ if (std::abs (mcParticle.pdgCode ()) != PDG_t::kLambda0 ) {
1617+ continue ;
1618+ }
1619+ if (std::abs (mcParticle.y ()) > ConfV0Rap) {
1620+ continue ;
1621+ }
1622+ auto pdg1 = mcParticle.pdgCode ();
1623+ auto kDaughters = mcParticle.daughters_as <aod::McParticles>();
1624+ int daughsize = 2 ;
1625+ if (kDaughters .size () != daughsize) {
1626+ continue ;
1627+ }
1628+ for (const auto & kCurrentDaughter : kDaughters ) {
1629+
1630+ if (std::abs (kCurrentDaughter .pdgCode ()) != PDG_t::kProton && std::abs (kCurrentDaughter .pdgCode ()) != PDG_t::kPiPlus ) {
1631+ continue ;
1632+ }
1633+ if (kCurrentDaughter .pdgCode () == PDG_t::kProton ) {
1634+ protonmc = ROOT::Math::PxPyPzMVector (kCurrentDaughter .px (), kCurrentDaughter .py (), kCurrentDaughter .pz (), o2::constants::physics::MassProton);
1635+ }
1636+ if (kCurrentDaughter .pdgCode () == PDG_t::kPiMinus ) {
1637+ antiPionmc = ROOT::Math::PxPyPzMVector (kCurrentDaughter .px (), kCurrentDaughter .py (), kCurrentDaughter .pz (), o2::constants::physics::MassPionCharged);
1638+ }
1639+
1640+ if (kCurrentDaughter .pdgCode () == PDG_t::kProtonBar ) {
1641+ antiProtonmc = ROOT::Math::PxPyPzMVector (kCurrentDaughter .px (), kCurrentDaughter .py (), kCurrentDaughter .pz (), o2::constants::physics::MassProton);
1642+ }
1643+ if (kCurrentDaughter .pdgCode () == PDG_t::kPiPlus ) {
1644+ pionmc = ROOT::Math::PxPyPzMVector (kCurrentDaughter .px (), kCurrentDaughter .py (), kCurrentDaughter .pz (), o2::constants::physics::MassPionCharged);
1645+ }
1646+ }
1647+ if (pdg1 == PDG_t::kLambda0 ) {
1648+ lambdadummymc = protonmc + antiPionmc;
1649+ histos.fill (HIST (" hSparseGenLambda" ), lambdadummymc.M (), lambdadummymc.Pt (), centrality);
1650+ }
1651+
1652+ if (pdg1 == PDG_t::kLambda0Bar ) {
1653+ antiLambdadummymc = antiProtonmc + pionmc;
1654+ histos.fill (HIST (" hSparseGenAntiLambda" ), antiLambdadummymc.M (), antiLambdadummymc.Pt (), centrality);
1655+ }
1656+ }
1657+ }
1658+ PROCESS_SWITCH (lambdapolsp, processMC, " Process MC" , false );
1659+
15081660 // Processing Event Mixing
1661+ /*
15091662 using BinningType = ColumnBinningPolicy<aod::collision::PosZ, aod::cent::CentFT0C>;
15101663 BinningType colBinning{{meGrp.axisVertex, meGrp.axisMultiplicityClass}, true};
15111664 Preslice<v0Candidates> tracksPerCollisionV0Mixed = o2::aod::v0data::straCollisionId; // for derived data only
@@ -1644,6 +1797,7 @@ struct lambdapolsp {
16441797 }
16451798 PROCESS_SWITCH(lambdapolsp, processDerivedDataMixed, "Process mixed event using derived data", false);
16461799
1800+
16471801 void processDerivedDataMixed2(soa::Join<aod::StraCollisions, aod::StraCents, aod::StraEvSels, aod::StraStamps, aod::StraZDCSP> const& collisions, v0Candidates const& V0s, dauTracks const&)
16481802 {
16491803 TRandom3 randGen(0);
@@ -1795,150 +1949,9 @@ struct lambdapolsp {
17951949 }
17961950 }
17971951 PROCESS_SWITCH(lambdapolsp, processDerivedDataMixed2, "Process mixed event2 using derived data", false);
1798-
1799- void processDerivedDataMixedFIFO (soa::Join<aod::StraCollisions, aod::StraCents, aod::StraEvSels, aod::StraStamps, aod::StraZDCSP> const & collisions, v0Candidates const & V0s, dauTracks const &)
1800- {
1801-
1802- auto nBins = colBinning.getAllBinsCount ();
1803- std::vector<std::deque<int >> eventPools (nBins); // Pool per bin holding just event indices
1804-
1805- for (auto & collision1 : collisions) {
1806-
1807- if (!collision1.sel8 ()) {
1808- continue ;
1809- }
1810- if (!collision1.triggereventsp ()) { // provided by StraZDCSP
1811- continue ;
1812- }
1813- if (rctCut.requireRCTFlagChecker && !rctChecker (collision1)) {
1814- continue ;
1815- }
1816-
1817- if (additionalEvSel && (!collision1.selection_bit (aod::evsel::kNoSameBunchPileup ) || !collision1.selection_bit (aod::evsel::kIsGoodZvtxFT0vsPV ))) {
1818- continue ;
1819- }
1820- if (additionalEvSel2 && (collision1.trackOccupancyInTimeRange () > cfgMaxOccupancy || collision1.trackOccupancyInTimeRange () < cfgMinOccupancy)) {
1821- continue ;
1822- }
1823- if (additionalEvSel3 && (!collision1.selection_bit (aod::evsel::kNoTimeFrameBorder ) || !collision1.selection_bit (aod::evsel::kNoITSROFrameBorder ))) {
1824- continue ;
1825- }
1826- if (additionalEvSel4 && !collision1.selection_bit (o2::aod::evsel::kIsGoodITSLayersAll )) {
1827- continue ;
1828- }
1829-
1830- int bin = colBinning.getBin (std::make_tuple (collision1.posZ (), collision1.centFT0C ()));
1831- auto groupV0_evt1 = V0s.sliceBy (tracksPerCollisionV0Mixed, collision1.index ());
1832- float centrality = collision1.centFT0C ();
1833- auto qxZDCA = collision1.qxZDCA ();
1834- auto qxZDCC = collision1.qxZDCC ();
1835- auto qyZDCA = collision1.qyZDCA ();
1836- auto qyZDCC = collision1.qyZDCC ();
1837- auto psiZDCC = collision1.psiZDCC ();
1838- auto psiZDCA = collision1.psiZDCA ();
1839- double modqxZDCA;
1840- double modqyZDCA;
1841- double modqxZDCC;
1842- double modqyZDCC;
1843-
1844- if (bin < 0 )
1845- continue ;
1846- modqxZDCA = TMath::Sqrt ((qxZDCA * qxZDCA) + (qyZDCA * qyZDCA)) * TMath::Cos (psiZDCA);
1847- modqyZDCA = TMath::Sqrt ((qxZDCA * qxZDCA) + (qyZDCA * qyZDCA)) * TMath::Sin (psiZDCA);
1848- modqxZDCC = TMath::Sqrt ((qxZDCC * qxZDCC) + (qyZDCC * qyZDCC)) * TMath::Cos (psiZDCC);
1849- modqyZDCC = TMath::Sqrt ((qxZDCC * qxZDCC) + (qyZDCC * qyZDCC)) * TMath::Sin (psiZDCC);
1850-
1851- auto psiZDC = TMath::ATan2 ((modqyZDCC - modqyZDCA), (modqxZDCC - modqxZDCA)); // full event plane from collision
1852-
1853- histos.fill (HIST (" hCentrality" ), centrality);
1854- histos.fill (HIST (" hpRes" ), centrality, (TMath::Cos (GetPhiInRange (psiZDCA - psiZDCC))));
1855-
1856- // For deduplication of (v0_evt1, v0_evt2) pairs per mixed event
1857- std::unordered_map<int , std::set<std::pair<int , int >>> seenMap;
1858-
1859- // Loop over Λ candidates in collision1 (keep psi from here)
1860-
1861- for (auto & v0_evt1 : groupV0_evt1) {
1862- if (!SelectionV0 (collision1, v0_evt1))
1863- continue ;
1864- bool LambdaTag1 = isCompatible (v0_evt1, 0 );
1865- bool aLambdaTag1 = isCompatible (v0_evt1, 1 );
1866- ROOT::Math::PxPyPzMVector proton1, pion1, antiproton1, antipion1, LambdaTag1dummy, AntiLambdaTag1dummy;
1867- if (LambdaTag1) {
1868- proton1 = {v0_evt1.pxpos (), v0_evt1.pypos (), v0_evt1.pzpos (), massPr};
1869- antipion1 = {v0_evt1.pxneg (), v0_evt1.pyneg (), v0_evt1.pzneg (), massPi};
1870- LambdaTag1dummy = proton1 + antipion1;
1871- }
1872- if (aLambdaTag1) {
1873- antiproton1 = {v0_evt1.pxneg (), v0_evt1.pyneg (), v0_evt1.pzneg (), massPr};
1874- pion1 = {v0_evt1.pxpos (), v0_evt1.pypos (), v0_evt1.pzpos (), massPi};
1875- AntiLambdaTag1dummy = antiproton1 + pion1;
1876- }
1877- if (shouldReject (LambdaTag1, aLambdaTag1, LambdaTag1dummy, AntiLambdaTag1dummy)) {
1878- continue ;
1879- }
1880- if (TMath::Abs (v0_evt1.eta ()) > 0.8 )
1881- continue ;
1882-
1883- // Loop over all FIFO pool events (mixed events) for this centrality bin
1884- int nMixedEvents = 0 ;
1885- for (auto it = eventPools[bin].rbegin (); it != eventPools[bin].rend () && nMixedEvents < meGrp.nMix ; ++it, ++nMixedEvents) {
1886- int collision2idx = *it;
1887- if (collision1.index () == collision2idx)
1888- continue ;
1889- auto groupV0_evt2 = V0s.sliceBy (tracksPerCollisionV0Mixed, collision2idx);
1890-
1891- // Now loop over Λ candidates in collision2 to randomize proton phi* (randomize decay angle)
1892- for (auto & v0_evt2 : groupV0_evt2) {
1893- if (!SelectionV0 (collision1, v0_evt2))
1894- continue ;
1895- bool LambdaTag2 = isCompatible (v0_evt2, 0 );
1896- bool aLambdaTag2 = isCompatible (v0_evt2, 1 );
1897- if (!LambdaTag2 && !aLambdaTag2)
1898- continue ;
1899-
1900- // Deduplicate (v0_evt1, v0_evt2) pairs per collision2idx
1901- auto key = std::make_pair (v0_evt1.index (), v0_evt2.index ());
1902- if (!seenMap[collision2idx].insert (key).second )
1903- continue ;
1904-
1905- ROOT::Math::PxPyPzMVector proton_mix, antiproton_mix, pion_mix, antipion_mix, LambdaTag2dummy, AntiLambdaTag2dummy;
1906- if (LambdaTag2) {
1907- proton_mix = {v0_evt2.pxpos (), v0_evt2.pypos (), v0_evt2.pzpos (), massPr};
1908- antipion_mix = {v0_evt2.pxneg (), v0_evt2.pyneg (), v0_evt2.pzneg (), massPi};
1909- LambdaTag2dummy = proton_mix + antipion_mix;
1910- }
1911- if (aLambdaTag2) {
1912- antiproton_mix = {v0_evt2.pxneg (), v0_evt2.pyneg (), v0_evt2.pzneg (), massPr};
1913- pion_mix = {v0_evt2.pxpos (), v0_evt2.pypos (), v0_evt2.pzpos (), massPi};
1914- AntiLambdaTag2dummy = antiproton_mix + pion_mix;
1915- }
1916- if (shouldReject (LambdaTag2, aLambdaTag2, LambdaTag2dummy, AntiLambdaTag2dummy)) {
1917- continue ;
1918- }
1919- if (TMath::Abs (v0_evt2.eta ()) > 0.8 )
1920- continue ;
1921- if (LambdaTag1) {
1922- double acvalue = 1.0 ;
1923- fillHistograms (1 , 0 , LambdaTag1dummy, proton_mix, psiZDCC, psiZDCA, psiZDC, centrality, v0_evt1.mLambda (), v0_evt1.pt (), v0_evt1.eta (), acvalue, 1.0 );
1924- }
1925- if (aLambdaTag1) {
1926- double acvalue = 1.0 ;
1927- fillHistograms (0 , 1 , AntiLambdaTag1dummy, antiproton_mix, psiZDCC, psiZDCA, psiZDC, centrality, v0_evt1.mAntiLambda (), v0_evt1.pt (), v0_evt1.eta (), acvalue, 1.0 );
1928- }
1929- }
1930- }
1931- }
1932- // After processing all mixes, add current event V0s to pool for future mixing
1933- eventPools[bin].push_back (collision1.index ());
1934- // Keep only N last events in FIFO queue
1935- if (static_cast <int >(eventPools[bin].size ()) > meGrp.nMix ) {
1936- eventPools[bin].pop_front ();
1937- }
1938- }
1939- }
1940- PROCESS_SWITCH (lambdapolsp, processDerivedDataMixedFIFO, " Process mixed event using derived data with FIFO method" , false );
1952+ */
19411953};
1954+
19421955WorkflowSpec defineDataProcessing (ConfigContext const & cfgc)
19431956{
19441957 return WorkflowSpec{
0 commit comments