Skip to content

Commit a7d8a4b

Browse files
wuctlbyCopilot
andcommitted
correlation of charm and bulk
Co-authored-by: Copilot <copilot@github.com>
1 parent 34cef08 commit a7d8a4b

1 file changed

Lines changed: 58 additions & 50 deletions

File tree

PWGHF/D2H/Tasks/taskPtFlucCharmHadrons.cxx

Lines changed: 58 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -109,8 +109,7 @@ struct HfTaskPtFlucCharmHadrons {
109109

110110
Filter filterSelectDplusCandidates = aod::hf_sel_candidate_dplus::isSelDplusToPiKPi >= selectionFlag;
111111
Filter filterSelectD0Candidates = aod::hf_sel_candidate_d0::isSelD0 >= selectionFlag || aod::hf_sel_candidate_d0::isSelD0bar >= selectionFlag;
112-
Filter filterSelectTracks = (nabs(aod::track::eta) < etaTrkMax) && (aod::track::pt > ptTrkMin) && (aod::track::pt < ptTrkMax) && (nabs(aod::track::dcaXY) < cfgCutDCAxy) && (nabs(aod::track::dcaZ) < cfgCutDCAz) && (aod::track::itsNCls >= cfgITScluster) && (aod::track::itsNClsInnerBarrel >= cfgITSbarrel) && (aod::track::tpcNClsFound >= cfgTPCcluster);
113-
112+
Filter filterSelectTracks = (nabs(aod::track::eta) < etaTrkMax) && (aod::track::pt > ptTrkMin) && (aod::track::pt < ptTrkMax) && (nabs(aod::track::dcaXY) < cfgCutDCAxy) && (nabs(aod::track::dcaZ) < cfgCutDCAz);
114113
Partition<CandD0DataWMl> selectedD0ToPiKWMl = aod::hf_sel_candidate_d0::isSelD0 >= selectionFlag;
115114
Partition<CandD0DataWMl> selectedD0ToKPiWMl = aod::hf_sel_candidate_d0::isSelD0bar >= selectionFlag;
116115

@@ -156,6 +155,8 @@ struct HfTaskPtFlucCharmHadrons {
156155
const AxisSpec aMPtTrkB{axisMPtTrkB, "Mean pT of tracks in subevent B (GeV/#it{c})"};
157156
const AxisSpec aPtCandProduct{axisPtCandProduct, "#it{p}_{T}^{cand} * <#it{p}_{T}>^{trks} (GeV^{2}/#it{c}^{2})"};
158157
const AxisSpec aPtTrkProduct{axisPtTrkProduct, "#it{p}_{T}^{trks}(A) * #it{p}_{T}^{trks}(B) (GeV^{2}/#it{c}^{2})"};
158+
const AxisSpec aNTrkA{axisNTrkA, "N_{tracks} in subevent A"};
159+
const AxisSpec aNTrkB{axisNTrkB, "N_{tracks} in subevent B"};
159160

160161
// Event-level accumulators (charged hadrons only!)
161162
registry.add("hEvents", "events vs cent", HistType::kTH1F, {aCent}, true);
@@ -180,6 +181,8 @@ struct HfTaskPtFlucCharmHadrons {
180181
registry.add("hMeanPtTrkAllColls", "Mean pT of charged hadrons for all collisions", HistType::kTHnSparseF, {aCent, aMPtTrkA, aMPtTrkB, aPtTrkProduct, aNTrkA, aNTrkB}, true);
181182
}
182183

184+
hfEvSel.addHistograms(registry); // collision monitoring
185+
183186
ccdb->setURL(ccdbUrl);
184187
ccdb->setCaching(true);
185188
ccdb->setLocalObjectValidityChecking();
@@ -188,43 +191,44 @@ struct HfTaskPtFlucCharmHadrons {
188191
// ---------------------------------------------------------------------------
189192
// Helper functions
190193
// ---------------------------------------------------------------------------
191-
/// Get the centrality
192-
/// \param collision is the collision with the centrality information
193-
double getCentrality(Colls::iterator const& collision)
194+
/// Check event selections for collision and fill event selection histograms, and revalculate centrality
195+
/// \param collision is the collision
196+
template <typename Coll>
197+
bool isSelectedHfCollision(Coll const& collision, float& cent)
194198
{
195-
double cent = -999.;
196-
switch (centEstimator) {
197-
case CentralityEstimator::FV0A:
198-
cent = collision.centFV0A();
199-
break;
200-
case CentralityEstimator::FT0M:
201-
cent = collision.centFT0M();
202-
break;
203-
case CentralityEstimator::FT0A:
204-
cent = collision.centFT0A();
205-
break;
206-
case CentralityEstimator::FT0C:
207-
cent = collision.centFT0C();
208-
break;
209-
default:
210-
LOG(warning) << "Centrality estimator not valid. Possible values are V0A, T0M, T0A, T0C. Fallback to V0A";
211-
cent = collision.centFV0A();
212-
break;
213-
}
214-
return cent;
199+
o2::hf_evsel::HfCollisionRejectionMask collRejMask{};
200+
if (centEstimator == CentralityEstimator::FT0A)
201+
{
202+
collRejMask = hfEvSel.getHfCollisionRejectionMask<true, CentralityEstimator::FT0A, aod::BCsWithTimestamps>(collision, cent, ccdb, registry);
203+
} else if (centEstimator == CentralityEstimator::FT0C)
204+
{
205+
collRejMask = hfEvSel.getHfCollisionRejectionMask<true, CentralityEstimator::FT0C, aod::BCsWithTimestamps>(collision, cent, ccdb, registry);
206+
} else if (centEstimator == CentralityEstimator::FT0M)
207+
{
208+
collRejMask = hfEvSel.getHfCollisionRejectionMask<true, CentralityEstimator::FT0M, aod::BCsWithTimestamps>(collision, cent, ccdb, registry);
209+
} else if (centEstimator == CentralityEstimator::FV0A)
210+
{
211+
collRejMask = hfEvSel.getHfCollisionRejectionMask<true, CentralityEstimator::FV0A, aod::BCsWithTimestamps>(collision, cent, ccdb, registry);
212+
} else
213+
{
214+
LOG(fatal) << "Centrality estimator not recognized for collision selection";
215+
std::abort();
216+
}
217+
hfEvSel.fillHistograms(collision, collRejMask, cent);
218+
return collRejMask == 0;
215219
}
216220

217221
/// Get candidate mass
218222
template <typename CandT, typename Trk>
219223
std::pair<float, float> getCandMassAndSign(const CandT& cand, DecayChannel channel, Trk const& /*tracks*/)
220224
{
221225
if constexpr (std::is_same_v<CandT, CandDplusDataWMl>) {
222-
return {HfHelper::invMassDplusToPiKPi(cand), cand.prong0_as<Trk>().sign()};
223-
} else if constexpr (std::is_same_v<CandT, CandD0DataWMl::value_type>) {
226+
return {HfHelper::invMassDplusToPiKPi(cand), cand.template prong0_as<Trk>().sign()};
227+
} else if constexpr (std::is_same_v<CandT, CandD0DataWMl>) {
224228
if (channel == DecayChannel::D0ToPiK) {
225-
return {HfHelper::invMassD0ToPiK(cand), candidate.isSelD0bar() ? 3 : 1}; // 3: reflected D0bar, 1: pure D0 excluding reflected D0bar
229+
return {HfHelper::invMassD0ToPiK(cand), cand.isSelD0bar() ? 3 : 1}; // 3: reflected D0bar, 1: pure D0 excluding reflected D0bar
226230
} else if (channel == DecayChannel::D0ToKPi) {
227-
return {HfHelper::invMassD0barToKPi(cand), candidate.isSelD0() ? 3 : 2}; // 3: reflected D0, 2: pure D0bar excluding reflected D0
231+
return {HfHelper::invMassD0barToKPi(cand), cand.isSelD0() ? 3 : 2}; // 3: reflected D0, 2: pure D0bar excluding reflected D0
228232
}
229233
}
230234
return {0., 0.}; // default return value for unsupported types
@@ -233,30 +237,31 @@ struct HfTaskPtFlucCharmHadrons {
233237
template <typename T>
234238
bool selectionTrack(const T& track) const
235239
{
236-
if (!(track.isGlobalTrack() && track.isPVContributor())) {
240+
if (!(track.isGlobalTrack() && track.isPVContributor() && track.itsNCls() > cfgITScluster.value && track.tpcNClsFound() > cfgTPCcluster.value && track.itsNClsInnerBarrel() >= cfgITSbarrel.value)) {
237241
return false;
238242
}
239243
return true;
240244
}
241245

242246
/// remove candidate daughters from the mean pT of tracks in A and B (if they are in the respective subevent)
243-
template <DecayChannel Channel, typename TrkType, typename Cand>
244-
float removeDaughtersFromMeanPt(const Cand& cand, float& meanPt, int& n, const std::vector<int>& trkIDs)
247+
template <DecayChannel Channel, typename CandT>
248+
float removeDaughtersFromMeanPt(const CandT& cand, const float& rawMeanPt, const int& n, const std::vector<int>& trkIDs)
245249
{
250+
float meanPt{0.f};
246251
if constexpr (Channel == DecayChannel::DplusToPiKPi) {
252+
std::array<int, 3> daugIDs = {cand.prong0Id(), cand.prong1Id(), cand.prong2Id()};
253+
std::array<float, 3> daugPts = {cand.ptProng0(), cand.ptProng1(), cand.ptProng2()};
247254
for (int iProng = 0; iProng < 3; ++iProng) { // for 3-prong
248-
int trkID = cand.template prong_as<TrkType>(iProng).globalIndex();
249-
float ptDaughter = cand.template prong_as<TrkType>(iProng).pt();
250-
if (std::find(trkIDs.begin(), trkIDs.end(), trkID) != trkIDs.end()) {
251-
meanPt = (meanPt * n - ptDaughter) / (n - 1);
255+
if (std::find(trkIDs.begin(), trkIDs.end(), daugIDs[iProng]) != trkIDs.end()) {
256+
meanPt = (rawMeanPt * n - daugPts[iProng]) / (n - 1);
252257
}
253258
}
254259
} else if constexpr (Channel == DecayChannel::D0ToPiK || Channel == DecayChannel::D0ToKPi) {
260+
std::array<int, 2> daugIDs = {cand.prong0Id(), cand.prong1Id()};
261+
std::array<float, 2> daugPts = {cand.ptProng0(), cand.ptProng1()};
255262
for (int iProng = 0; iProng < 2; ++iProng) { // for 2-prong
256-
int trkID = cand.template prong_as<TrkType>(iProng).globalIndex();
257-
float ptDaughter = cand.template prong_as<TrkType>(iProng).pt();
258-
if (std::find(trkIDs.begin(), trkIDs.end(), trkID) != trkIDs.end()) {
259-
meanPt = (meanPt * n - ptDaughter) / (n - 1);
263+
if (std::find(trkIDs.begin(), trkIDs.end(), daugIDs[iProng]) != trkIDs.end()) {
264+
meanPt = (rawMeanPt * n - daugPts[iProng]) / (n - 1);
260265
}
261266
}
262267
}
@@ -338,16 +343,17 @@ struct HfTaskPtFlucCharmHadrons {
338343
ml2 >= mlTwoMin.value && ml2 < mlTwoMax.value);
339344
}
340345

341-
/// Compute the scalar product
342-
/// \param collision is the collision with the Q vector information and event plane
343-
/// \param candidates are the selected candidates
346+
/// Compute the mean pT of the event using charged tracks in two eta-separated subevents, and correlate with D candidates
347+
/// \param collision is the collision with centrality and event selection
348+
/// \param candidates are the D candidates to correlate with the mean pT of the event
349+
/// \param tracks are the tracks used to compute the mean pT of the event
344350
template <DecayChannel Channel, typename T1, typename Trk>
345351
void runPtFlucAnalysis(Colls::iterator const& collision,
346352
T1 const& candidates,
347353
Trk const& tracks)
348354
{
349-
float cent = getCentrality(collision);
350-
if (cent < centralityMin || cent > centralityMax) {
355+
float cent{0.f};
356+
if (!isSelectedHfCollision(collision, cent)) {
351357
return;
352358
}
353359

@@ -397,24 +403,26 @@ struct HfTaskPtFlucCharmHadrons {
397403

398404
// remove the daughters from the mean pT of tracks and calculate pt product
399405
float eta = cand.eta();
406+
float pt = cand.pt();
407+
400408
float candPtProduct{0.f};
401409
float meanPtA{0.f};
402410
float meanPtB{0.f};
403411
if (eta > etaAMin.value && eta < etaAMax.value) {
404-
meanPtB = removeDaughtersFromMeanPt<Channel, Trk>(cand, RawMeanPtB, nB, trkIDB);
412+
meanPtB = removeDaughtersFromMeanPt<Channel, decltype(cand)>(cand, RawMeanPtB, nB, trkIDB);
405413
meanPtA = RawMeanPtA; // no need to remove daughters from A if candidate is in A
406-
candPtProduct = cand.pt() * meanPtB;
414+
candPtProduct = pt * meanPtB;
407415
} else if (eta > etaBMin.value && eta < etaBMax.value) {
408-
meanPtA = removeDaughtersFromMeanPt<Channel, Trk>(cand, RawMeanPtA, nA, trkIDA);
416+
meanPtA = removeDaughtersFromMeanPt<Channel, decltype(cand)>(cand, RawMeanPtA, nA, trkIDA);
409417
meanPtB = RawMeanPtB; // no need to remove daughters from B if candidate is in B
410-
candPtProduct = cand.pt() * meanPtA;
418+
candPtProduct = pt * meanPtA;
411419
}
412420

413421
// get candidate mass and sign
414422
auto [invMass, sign] = getCandMassAndSign(cand, Channel, tracks);
415423

416424
// fill charm-bulk correlation thnsparse
417-
registry.fill(HIST("hCharmBulkCorrelations"), invMass, cent, cand.pt(), sign, ml1, ml2, eta, meanPtA, meanPtB, candPtProduct);
425+
registry.fill(HIST("hCharmBulkCorrelations"), invMass, cent, pt, sign, ml1, ml2, eta, meanPtA, meanPtB, candPtProduct);
418426
}
419427
} else
420428
{

0 commit comments

Comments
 (0)