AliPhysics  608b256 (608b256)
AliAnalysisTaskEmcalJetHPerformance.cxx
Go to the documentation of this file.
1 
6 
7 #include <map>
8 #include <vector>
9 #include <iostream>
10 #include <bitset>
11 
12 #include <TObject.h>
13 #include <TCollection.h>
14 #include <TAxis.h>
15 #include <THnSparse.h>
16 
17 #include <AliAnalysisManager.h>
18 #include <AliInputEventHandler.h>
19 #include <AliLog.h>
20 
21 #include "yaml-cpp/yaml.h"
23 #include "AliTrackContainer.h"
24 #include "AliClusterContainer.h"
25 #include "AliEmcalContainerUtils.h"
26 #include "AliJetContainer.h"
27 #include "AliEmcalJet.h"
28 
30 
32 
33 namespace PWGJE {
34 namespace EMCALJetTasks {
35 
40  AliAnalysisTaskEmcalJet("AliAnalysisTaskEmcalJetHPerformance", kFALSE),
41  fYAMLConfig(),
42  fConfigurationInitialized(false),
43  fHistManager(),
44  fEmbeddingQA(),
45  fCreateQAHists(false),
46  fCreateResponseMatrix(false),
47  fEmbeddedCellsName("emcalCells"),
48  fPreviousEventTrigger(0),
49  fPreviousEmbeddedEventSelected(false),
50  fResponseMatrixFillMap(),
51  fResponseFromThreeJetCollections(true),
52  fMinFractionShared(0.),
53  fLeadingHadronBiasType(AliAnalysisTaskEmcalJetHUtils::kCharged)
54 {
55 }
56 
61  AliAnalysisTaskEmcalJet(name, kTRUE),
62  fYAMLConfig(),
64  fHistManager(name),
65  fEmbeddingQA(),
66  fCreateQAHists(false),
67  fCreateResponseMatrix(false),
68  fEmbeddedCellsName("emcalCells"),
75 {
76  // Ensure that additional general histograms are created
78 }
79 
84  fYAMLConfig(other.fYAMLConfig),
86  fHistManager(other.fHistManager.GetName()),
87  //fEmbeddingQA(other.fEmbeddingQA), // Cannot use because the THistManager (which is in the class) copy constructor is private.
95 {
96  TIter next(other.fHistManager.GetListOfHistograms());
97  TObject* obj = 0;
98  while ((obj = next())) {
99  fHistManager.SetObject(obj, obj->GetName());
100  }
101 }
102 
108 {
109  swap(*this, other);
110  return *this;
111 }
112 
117 {
118  // Base class options
119  // Recycle unused embedded events
120  fYAMLConfig.GetProperty("recycleUnusedEmbeddedEventsMode", fRecycleUnusedEmbeddedEventsMode, false);
121  // Task physics (trigger) selection.
122  std::vector<std::string> physicsSelection;
123  bool res = fYAMLConfig.GetProperty(std::vector<std::string>({"eventCuts", "physicsSelection"}), physicsSelection, false);
124  if (res) {
125  fOfflineTriggerMask = AliEmcalContainerUtils::DeterminePhysicsSelectionFromYAML(physicsSelection);
126  }
127 
128  // Same ordering as in the constructor (for consistency)
129  std::string baseName = "enable";
130  // These are disabled by default.
131  fYAMLConfig.GetProperty({baseName, "QAHists"}, fCreateQAHists, false);
132  fYAMLConfig.GetProperty({baseName, "responseMatrix"}, fCreateResponseMatrix, false);
133 
134  // Event cuts
135  baseName = "eventCuts";
136  // If event cuts are enabled (which they exceptionally are by default), then we want to configure them here.
137  // If the event cuts are explicitly disabled, then we invert that value to enable the AliAnylsisTaskEmcal
138  // builtin event selection.
139  bool tempBool;
140  fYAMLConfig.GetProperty({baseName, "enabled"}, tempBool, false);
141  fUseBuiltinEventSelection = !tempBool;
142  if (fUseBuiltinEventSelection == false) {
143  // Need to include the namespace so that AliDebug will work properly...
144  std::string taskName = "PWGJE::EMCALJetTasks::";
145  taskName += GetName();
146  AliAnalysisTaskEmcalJetHUtils::ConfigureEventCuts(fAliEventCuts, fYAMLConfig, fOfflineTriggerMask, baseName, taskName);
147  }
148 
149  // General task options
150  baseName = "general";
151  fYAMLConfig.GetProperty({baseName, "nCentBins"}, fNcentBins, false);
152 
153  // QA options
154  baseName = "QA";
155  fYAMLConfig.GetProperty({baseName, "cellsName"}, fCaloCellsName, false);
156  // Defaults to "emcalCells" if not set.
157  fYAMLConfig.GetProperty({baseName, "embeddedCellsName"}, fEmbeddedCellsName, false);
158 
159  // Response matrix properties
160  baseName = "responseMatrix";
161  fYAMLConfig.GetProperty({baseName, "useThreeJetCollections"}, fResponseFromThreeJetCollections, false);
162  fYAMLConfig.GetProperty({baseName, "minFractionSharedPt"}, fMinFractionShared, false);
163  std::string hadronBiasStr = "";
164  baseName = "jets";
165  res = fYAMLConfig.GetProperty({baseName, "leadingHadronBiasType"}, hadronBiasStr, false);
166  // Only attempt to set the property if it is retrieved successfully
167  if (res) {
169  }
170 }
171 
176 {
177  std::string baseName = "jets";
178  std::vector <std::string> jetNames = {"hybridLevelJets", "detLevelJets", "partLevelJets", "analysisJets"};
179  for (const auto & jetName : jetNames) {
180  // Retrieve the node just to see if it is exists. If so, then we can proceed
181  YAML::Node node;
182  bool res = fYAMLConfig.GetProperty(std::vector<std::string>({baseName, jetName}), node, false);
183  if (res) {
184  // Retrieve jet container properties
185  std::string collectionName = "", acceptance = "";
186  double R = -1;
187  fYAMLConfig.GetProperty({baseName, jetName, "collection"}, collectionName, true);
188  fYAMLConfig.GetProperty({baseName, jetName, "acceptance"}, acceptance, true);
189  fYAMLConfig.GetProperty({baseName, jetName, "R"}, R, true);
190 
191  // Create jet container and set the name
192  AliDebugStream(1) << "Creating jet from jet collection name " << collectionName << " with acceptance " << acceptance << " and R=" << R << "\n";
193  AliJetContainer * jetCont = AddJetContainer(collectionName.c_str(), acceptance.c_str(), R);
194  jetCont->SetName(jetName.c_str());
195 
196  // Leading hadron type
197  int leadingHadronType = -1;
198  bool res = fYAMLConfig.GetProperty({baseName, jetName, "leadingHadronType"}, leadingHadronType, false);
199  if (res) {
200  AliDebugStream(1) << "Setting leading hadron type of " << leadingHadronType << " for jet cont " << jetName << "\n";
201  jetCont->SetLeadingHadronType(leadingHadronType);
202  }
203  }
204  else {
205  AliInfoStream() << "Unable to find definition of jet container corresponding to \"" << jetName << "\"\n";
206  }
207  }
208 }
209 
214 {
216 
217  // Ensure that we have at least one configuration in the YAML config.
218  if (fYAMLConfig.DoesConfigurationExist(0) == false) {
219  // No configurations exist. Return immediately.
221  }
222 
223  // Always initialize for streaming purposes
225 
226  // Setup task based on the properties defined in the YAML config
227  AliDebugStream(2) << "Configuring task from the YAML configuration.\n";
230  AliDebugStream(2) << "Finished configuring via the YAML configuration.\n";
231 
232  // Print the results of the initialization
233  // Print outside of the ALICE Log system to ensure that it is always available!
234  std::cout << *this;
235 
238 }
239 
244 {
245  // First call the base class
247 
248  // Check that the task was initialized
250  AliFatal("Task was not initialized. Please ensure that Initialize() was called!");
251  }
252  // Reinitialize the YAML configuration
254 
255  // Create histograms
256  if (fCreateQAHists) {
257  SetupQAHists();
258  }
259  if (fCreateResponseMatrix) {
261  }
262 
263  // Store hist manager output in the output list
264  TIter next(fHistManager.GetListOfHistograms());
265  TObject* obj = 0;
266  while ((obj = next())) {
267  fOutput->Add(obj);
268  }
269 
270  // Initialize
272  if (embeddingHelper) {
273  bool res = fEmbeddingQA.Initialize();
274  if (res) {
276  }
277  }
278 
279  // Post the data when finished
280  PostData(1, fOutput);
281 }
282 
290 {
291  std::string name = prefix + "/fHistCellEnergy";
292  std::string title = name + ";\\mathit{E}_{\\mathrm{cell}} (\\mathrm{GeV});counts";
293  fHistManager.CreateTH1(name.c_str(), title.c_str(), 300, 0, 150);
294 
295  name = prefix + "/fHistCellTime";
296  title = name + ";t (s);counts";
297  fHistManager.CreateTH1(name.c_str(), title.c_str(), 1000, -10e-6, 10e-6);
298 
299  name = prefix + "/fHistNCells";
300  title = name + ";\\mathrm{N}_{\\mathrm{cells}};counts";
301  fHistManager.CreateTH1(name.c_str(), title.c_str(), 100, 0, 5000);
302 
303  name = prefix + "/fHistCellID";
304  title = name + ";\\mathrm{N}_{\\mathrm{cell}};counts";
305  fHistManager.CreateTH1(name.c_str(), title.c_str(), 20000, 0, 20000);
306 
307  // Histograms for embedding QA which use the cell timing to determine whether the
308  // embedded event has been double corrected.
309  if (prefix.find("embedding") != std::string::npos) {
310  name = prefix + "/fHistEmbeddedEventUsed";
311  title = name + ";Embedded event used";
312  fHistManager.CreateTH1(name.c_str(), title.c_str(), 2, 0, 2);
313 
314  name = prefix + "/fHistInternalEventSelection";
315  title = name + ";Embedded event used;Trigger bit";
316  fHistManager.CreateTH2(name.c_str(), title.c_str(), 2, 0, 2, 32, -0.5, 31.5);
317  }
318 }
319 
324 {
325  std::string prefix = "QA/";
326  prefix += fCaloCellsName.Data();
328  auto embeddingInstance = AliAnalysisTaskEmcalEmbeddingHelper::GetInstance();
329  if (embeddingInstance) {
330  prefix = "QA/embedding/";
331  prefix += fEmbeddedCellsName;
333  }
334 }
335 
340 {
341  // Cell level QA
343 
344  // Clusters
345  AliEmcalContainer* cont = 0;
346  TIter nextClusColl(&fClusterCollArray);
347  while ((cont = static_cast<AliClusterContainer*>(nextClusColl()))) {
348  // Cluster time vs energy
349  std::string name = "QA/%s/fHistClusterEnergyVsTime";
350  std::string title = name + ";E_{cluster} (GeV);t_{cluster} (s)";
351  fHistManager.CreateTH2(TString::Format(name.c_str(), cont->GetName()), TString::Format(title.c_str(), cont->GetName()), 1000, 0, 100, 300, -300e-9, 300e-9);
352  }
353 
354  // Jets
355  TIter nextJetColl(&fJetCollArray);
356  while ((cont = static_cast<AliJetContainer*>(nextJetColl()))) {
357  // Jet pT
358  std::string name = "QA/%s/fHistJetPt";
359  std::string title = name + ";p_{T} (GeV)";
360  fHistManager.CreateTH1(TString::Format(name.c_str(), cont->GetName()), TString::Format(title.c_str(), cont->GetName()), 500, 0, 250);
361  }
362 }
363 
368 {
369  // Main response matrix THnSparse
370  std::string name = "response/fHistResponseMatrix";
371  std::string title = name;
372 
373  // Retrieve binning from the YAML configuration
374  std::vector<TAxis *> binning;
375  // This structure is designed to preserve the order of the axis in the YAML by using a YAML sequence (decoded into
376  // a vector), while defining a pair of the axis name and axis limts. Using this structure avoids the need to create
377  // a new object and conversion to retrieve the data
378  std::vector<std::pair<std::string, std::vector<double>>> sparseAxes;
379  std::string baseName = "responseMatrix";
380  fYAMLConfig.GetProperty({baseName, "axes"}, sparseAxes, true);
381  for (auto axis : sparseAxes) {
382  auto axisLimits = axis.second;
383  AliDebugStream(3) << "Creating axis " << axis.first << " with nBins " << axisLimits.at(0) << ", min: " << axisLimits.at(1) << ", max: " << axisLimits.at(2) << "\n";
384  binning.emplace_back(new TAxis(axisLimits.at(0), axisLimits.at(1), axisLimits.at(2)));
385  }
386 
387  // "s" ensures that Sumw2() is called
388  // The explicit const_cast is required
389  THnSparse * hist = fHistManager.CreateTHnSparse(name.c_str(), title.c_str(), binning.size(), const_cast<const TAxis **>(binning.data()), "s");
390  // Set the axis titles
391  int axisNumber = 0;
392  for (auto axis = sparseAxes.begin(); axis != sparseAxes.end(); axis++) {
393  AliDebugStream(5) << "ResponseMatrix: Add axis " << axis->first << " to sparse\n";
394  hist->GetAxis(axisNumber)->SetTitle(axis->first.c_str());
395  axisNumber++;
396  }
397 
398  // Define mapping from value name to value (including jet information)
399  for (unsigned int iJet = 1; iJet < 3; iJet++)
400  {
401  // pt
402  // ex: p_{T,1}
403  fResponseMatrixFillMap.insert(std::make_pair(std::string("p_{T,") + std::to_string(iJet) + "}", std::make_pair(iJet, &ResponseMatrixFillWrapper::fPt)));
404  // Area
405  // ex: A_{jet,1}
406  fResponseMatrixFillMap.insert(std::make_pair(std::string("A_{jet,") + std::to_string(iJet) + "}", std::make_pair(iJet, &ResponseMatrixFillWrapper::fArea)));
407  // EP angle
408  // ex: #theta_{jet,1}^{EP}
409  fResponseMatrixFillMap.insert(std::make_pair(std::string("#theta_{jet,") + std::to_string(iJet) + "}^{EP}", std::make_pair(iJet, &ResponseMatrixFillWrapper::fRelativeEPAngle)));
410  // Leading hadron
411  // ex: p_{T,particle,1}^{leading} (GeV/c)
412  fResponseMatrixFillMap.insert(std::make_pair(std::string("p_{T,particle,") + std::to_string(iJet) + "}^{leading} (GeV/c)", std::make_pair(iJet, &ResponseMatrixFillWrapper::fLeadingHadronPt)));
413  }
414  // Distance from one jet to another
415  fResponseMatrixFillMap.insert(std::make_pair("distance", std::make_pair(1, &ResponseMatrixFillWrapper::fDistance)) );
416  // Centrality
417  fResponseMatrixFillMap.insert(std::make_pair("centrality", std::make_pair(1, &ResponseMatrixFillWrapper::fCentrality)) );
418 
419  // Shared momentum fraction
420  name = "fHistFractionSharedPt";
421  title = "Fraction of p_{T} shared between matched jets";
422  // Need to include the bin from 1-1.01 to ensure that jets which shared all of their momentum
423  // due not end up in the overflow bin!
424  fHistManager.CreateTH1(name.c_str(), title.c_str(), 101, 0, 1.01);
425 }
426 
431 {
432  // Only fill the embedding qa plots if:
433  // - We are using the embedding helper
434  // - The class has been initialized
435  if (fEmbeddingQA.IsInitialized()) {
437  }
438 
439  if (fCreateQAHists) {
440  QAHists();
441  }
442  if (fCreateResponseMatrix) {
443  ResponseMatrix();
444  }
445 
446  return kTRUE;
447 }
448 
453 {
454  // No additional processing is necessary
455  // Continue on to filling the histograms
456  FillQAHists();
457 }
458 
466 void AliAnalysisTaskEmcalJetHPerformance::FillCellQAHists(const std::string & prefix, AliVCaloCells * cells)
467 {
468  AliDebugStream(4) << "Storing cells with prefix \"" << prefix << "\". N cells: " << cells->GetNumberOfCells() << "\n";
469  short absId = -1;
470  double eCell = 0;
471  double tCell = 0;
472  double eFrac = 0;
473  int mcLabel = -1;
474 
475  std::string energyName = prefix + "/fHistCellEnergy";
476  std::string timeName = prefix + "/fHistCellTime";
477  std::string idName = prefix + "/fHistCellID";
478  bool embeddedCellWithLateCellTime = false;
479  bool fillingEmbeddedCells = (prefix.find("embedding") != std::string::npos);
480  for (unsigned int iCell = 0; iCell < cells->GetNumberOfCells(); iCell++) {
481  cells->GetCell(iCell, absId, eCell, tCell, mcLabel, eFrac);
482 
483  AliDebugStream(5) << "Cell " << iCell << ": absId: " << absId << ", E: " << eCell << ", t: " << tCell
484  << ", mcLabel: " << mcLabel << ", eFrac: " << eFrac << "\n";
485  fHistManager.FillTH1(energyName.c_str(), eCell);
486  fHistManager.FillTH1(timeName.c_str(), tCell);
487  fHistManager.FillTH1(idName.c_str(), absId);
488 
489  // We will record the event selection if the time is less than -400 ns
490  // This corresponds to a doubly corrected embedded event, which shouldn't be possible, and therefore
491  // indicates that something has gone awry
492  // NOTE: We must also require that the time is greater than -1 because apparently some uncalibrated cells
493  // will report their time as -1. We don't want to include those cells.
494  if (tCell < -400e-9 && tCell > -1 && fillingEmbeddedCells) {
495  embeddedCellWithLateCellTime = true;
496  }
497  }
498 
499  // If we have one embedded cell with late cell time, then we want to fill out the QA to
500  // help identify the event.
501  std::string embeddedEventUsed = prefix + "/fHistEmbeddedEventUsed";
502  std::string embeddedInteranlEventSelection = prefix + "/fHistInternalEventSelection";
503  if (embeddedCellWithLateCellTime)
504  {
505  auto embeddingInstance = AliAnalysisTaskEmcalEmbeddingHelper::GetInstance();
506  if (embeddingInstance) {
507  fHistManager.FillTH1(embeddedEventUsed.c_str(),
508  static_cast<double>(fPreviousEmbeddedEventSelected));
509 
510  // Determine the physics selection. This isn't quite a perfect way to store it, as it mingles the
511  // selections between different events. But it is simple, which will let us investigate quickly.
512  // Plus, it's a reasonable bet that the event selection when be the same when it goes wrong.
513  std::bitset<sizeof(UInt_t) * 8> testBits = fPreviousEventTrigger;
514  for (unsigned int i = 0; i < 32; i++) {
515  if (testBits.test(i)) {
516  fHistManager.FillTH2(embeddedInteranlEventSelection.c_str(),
517  static_cast<double>(fPreviousEmbeddedEventSelected), i);
518  }
519  }
520  }
521  }
522 
523  std::string nCellsName = prefix + "/fHistNCells";
524  fHistManager.FillTH1(nCellsName.c_str(), cells->GetNumberOfCells());
525 }
526 
531 {
532  // Fill standard cell QA
533  std::string prefix = "QA/";
534  prefix += fCaloCellsName.Data();
535  FillCellQAHists(prefix, fCaloCells);
536 
537  // Fill embedded cell QA it if's available.
538  auto embeddingInstance = AliAnalysisTaskEmcalEmbeddingHelper::GetInstance();
539  if (embeddingInstance) {
540  auto embeddedCells = dynamic_cast<AliVCaloCells*>(
541  embeddingInstance->GetExternalEvent()->FindListObject(fEmbeddedCellsName.c_str()));
542  if (embeddedCells) {
543  prefix = "QA/embedding/";
544  prefix += fEmbeddedCellsName;
545  FillCellQAHists(prefix, embeddedCells);
546  }
547  }
548 }
549 
554 {
555  FillCellQAHists();
556 
557  // Clusters
558  AliClusterContainer* clusCont = 0;
559  TIter nextClusColl(&fClusterCollArray);
560  AliVCluster * cluster = 0;
561  while ((clusCont = static_cast<AliClusterContainer*>(nextClusColl()))) {
562  for (auto clusIter : clusCont->accepted_momentum())
563  {
564  cluster = clusIter.second;
565  // Intentionally plotting against raw energy
566  fHistManager.FillTH2(TString::Format("QA/%s/fHistClusterEnergyVsTime", clusCont->GetName()), cluster->E(), cluster->GetTOF());
567  }
568  }
569 
570  // Jets
571  AliJetContainer * jetCont = 0;
572  TIter nextJetColl(&fJetCollArray);
573  while ((jetCont = static_cast<AliJetContainer*>(nextJetColl()))) {
574  for (auto jet : jetCont->accepted())
575  {
576  fHistManager.FillTH1(TString::Format("QA/%s/fHistJetPt", jetCont->GetName()), jet->Pt());
577  }
578  }
579 
580  // Update the previous event trigger to the current event trigger so that it is available next event.
581  // This is stored for keeping track of when embedded events are double corrected.
582  // This must be updated after filling the relevant hists above!
584  ((AliInputEventHandler*)(AliAnalysisManager::GetAnalysisManager()->GetInputEventHandler()))->IsEventSelected();
585  auto embeddingInstance = AliAnalysisTaskEmcalEmbeddingHelper::GetInstance();
586  if (embeddingInstance) {
587  fPreviousEmbeddedEventSelected = embeddingInstance->EmbeddedEventUsed();
588  }
589 }
590 
595 {
596  AliJetContainer * jetsHybrid = GetJetContainer("hybridLevelJets");
597  AliJetContainer * jetsDetLevel = GetJetContainer("detLevelJets");
598  AliJetContainer * jetsPartLevel = GetJetContainer("partLevelJets");
599  if (!jetsHybrid) {
600  AliErrorStream() << "Could not retrieve hybrid jet collection.\n";
601  return;
602  }
603  if (!jetsDetLevel) {
604  AliErrorStream() << "Could not retrieve det level jet collection.\n";
605  return;
606  }
607  if (fResponseFromThreeJetCollections && !jetsPartLevel) {
608  AliErrorStream() << "Could not retrieve part level jet collection.\n";
609  return;
610  }
611 
612  // Handle matching of jets.
613  for (auto jet1 : jetsHybrid->accepted())
614  {
615  AliDebugStream(4) << "jet1: " << jet1->toString() << "\n";
616  AliDebugStream(4) << "jet1 address: " << jet1 << "\n";
617 
618  // Get jet the det level jet from the hybrid jet
619  AliEmcalJet * jet2 = jet1->ClosestJet();
620  if(!jet2) continue;
621 
622  AliDebugStream(4) << "jet2: " << jet2->toString() << "\n";
623  AliDebugStream(4) << "jet2 address: " << jet2 << "\n";
624 
625  // Check shared fraction
626  double sharedFraction = jetsHybrid->GetFractionSharedPt(jet1);
627  fHistManager.FillTH1("fHistFractionSharedPt", sharedFraction);
628  if (sharedFraction < fMinFractionShared) {
629  AliDebugStream(4) << "Rejecting jet due to momentum fraction of " << sharedFraction << ", smaller than the minimum.\n";
630  continue;
631  }
632  else {
633  AliDebugStream(4) << "Jet passed momentum fraction cut with value of " << sharedFraction << "\n";
634  }
635 
636  // Apply additional selection to jet 2
637  // TODO: Should we apply acceptance criteria to jet 2 here?
638 
639  // Get MC level jet
640  AliEmcalJet * jetToPass = 0;
642  AliEmcalJet * jet3 = jet2->ClosestJet();
643 
644  // Accept jet 3
645  UInt_t rejectionReason = 0;
646  if (!jetsPartLevel->AcceptJet(jet3, rejectionReason)) {
647  // TODO: Store rejection reasons
648  //fHistRejectionReason2->Fill(jets2->GetRejectionReasonBitPosition(rejectionReason), jet2->Pt());
649  continue;
650  }
651 
652  AliDebugStream(4) << "jet3: " << jet3->toString() << "\n";
653  AliDebugStream(4) << "jet3 address: " << jet3 << "\n";
654 
655  // Use for the response
656  AliDebugStream(4) << "Using part level jet for response\n";
657  jetToPass = jet3;
658  }
659  else {
660  // Use for the response
661  AliDebugStream(4) << "Using det level jet for response\n";
662  jetToPass = jet2;
663  }
664 
665  // Fill response
666  FillResponseMatrix(jet1, jetToPass);
667  }
668 
669 }
670 
675 {
676  if (!jet1 || !jet2) {
677  AliErrorStream() << "Null jet passed to fill response matrix";
678  }
679 
680  AliDebugStream(3) << "About to create ResponseMatrixFillWrappers\n";
681  AliDebugStream(4) << "jet1: " << jet1->toString() << "\n";
682  AliDebugStream(4) << "jet2: " << jet2->toString() << "\n";
683  // Create map from jetNumber to jet and initialize the objects
684  std::map<unsigned int, ResponseMatrixFillWrapper> jetNumberToJet = {
685  std::make_pair(1, CreateResponseMatrixFillWrapper(jet1)),
686  std::make_pair(2, CreateResponseMatrixFillWrapper(jet2))
687  };
688 
689  // Fill histograms
690  std::string histName = "response/fHistResponseMatrix";
691  std::vector<double> values;
692  THnSparse * response = static_cast<THnSparse*>(fHistManager.FindObject(histName.c_str()));
693  AliDebugStream(3) << "About to fill response matrix values\n";
694  AliDebugStream(4) << "jet1: " << jet1->toString() << "\n";
695  AliDebugStream(4) << "jet2: " << jet2->toString() << "\n";
696  for (unsigned int i = 0; i < response->GetNdimensions(); i++) {
697  std::string title = response->GetAxis(i)->GetTitle();
698 
699  // Retrieve pair of jet and pointer to extract the fill value
700  auto jetPair = fResponseMatrixFillMap.find(title);
701  if (jetPair != fResponseMatrixFillMap.end()) {
702  auto wrapper = jetNumberToJet.at(jetPair->second.first);
703  auto member = jetPair->second.second;
704  AliDebugStream(4) << "Filling value " << wrapper.*member << " into axis " << title << "\n";
705  values.emplace_back(wrapper.*member);
706  }
707  else {
708  AliWarningStream() << "Unable to fill dimension " << title << "!\n";
709  }
710  }
711 
712  fHistManager.FillTHnSparse(histName.c_str(), values.data());
713 }
714 
719 {
721  if (!jet) {
722  AliErrorStream() << "Must pass valid jet to create object.\n";
723  return wrapper;
724  }
725  wrapper.fPt = jet->Pt();
726  wrapper.fArea = jet->Area();
727  wrapper.fPhi = jet->Phi();
728  wrapper.fDistance = jet->ClosestJetDistance();
729  wrapper.fCentrality = fCent;
732 
733  return wrapper;
734 }
735 
742 {
743  // Get the pointer to the existing analysis manager via the static access method.
744  //==============================================================================
745  AliAnalysisManager *mgr = AliAnalysisManager::GetAnalysisManager();
746  if (!mgr)
747  {
748  AliErrorClass("No analysis manager to connect to.");
749  return nullptr;
750  }
751 
752  // Setup task name
753  std::string taskName = "AliAnalysisTaskEmcalJetHPerformance";
754  std::string suffixName(suffix);
755  if (suffixName != "") {
756  taskName += "_";
757  taskName += suffixName;
758  }
759 
760  // Create task and configure as desired.
762  // Set a few general default.
763  task->SetNCentBins(5);
764  // Configuration is via YAML.
765  mgr->AddTask(task);
766 
767  // Create containers for input/output
768  mgr->ConnectInput(task, 0, mgr->GetCommonInputContainer() );
769  AliAnalysisDataContainer * outputContainer = mgr->CreateContainer(task->GetName(),
770  TList::Class(),
771  AliAnalysisManager::kOutputContainer,
772  Form("%s", AliAnalysisManager::GetCommonFileName()));
773  mgr->ConnectOutput(task, 1, outputContainer);
774 
775  return task;
776 }
777 
784 {
785  std::stringstream tempSS;
786  tempSS << std::boolalpha;
787  tempSS << "Recycle unused embedded events: " << fRecycleUnusedEmbeddedEventsMode << "\n";
788  tempSS << "Jet collections:\n";
789  TIter next(&fJetCollArray);
790  AliJetContainer * jetCont;
791  while ((jetCont = static_cast<AliJetContainer *>(next()))) {
792  tempSS << "\t" << jetCont->GetName() << ": " << jetCont->GetArrayName() << "\n";
793  }
794  tempSS << "AliEventCuts\n";
795  tempSS << "\tEnabled: " << !fUseBuiltinEventSelection << "\n";
796  tempSS << "QA Hists:\n";
797  tempSS << "\tEnabled: " << fCreateQAHists << "\n";
798  tempSS << "Response matrix:\n";
799  tempSS << "\tEnabled: " << fCreateResponseMatrix << "\n";
800  tempSS << "\tConstruct response from 3 jet collections: " << fResponseFromThreeJetCollections << "\n";
801  tempSS << "\tMin fraction shared pt: " << fMinFractionShared << "\n";
802  tempSS << "\tJet leading hadron bias type: " << fLeadingHadronBiasType << "\n";
803  tempSS << "\tResponse matrix fill map: \n";
804  for (auto el : fResponseMatrixFillMap) {
805  tempSS << "\t\tProperty " << el.first << " applied to jet " << el.second.first << "\n";
806  }
807 
808  return tempSS.str();
809 }
810 
817 std::ostream & AliAnalysisTaskEmcalJetHPerformance::Print(std::ostream & in) const {
818  in << toString();
819  return in;
820 }
821 
829 {
830  Printf("%s", toString().c_str());
831 }
832 
833 } /* namespace EMCALJetTasks */
834 } /* namespace PWGJE */
835 
843 std::ostream & operator<<(std::ostream & in, const PWGJE::EMCALJetTasks::AliAnalysisTaskEmcalJetHPerformance & myTask)
844 {
845  std::ostream & result = myTask.Print(in);
846  return result;
847 }
848 
855 {
856  using std::swap;
857 
858  // Same ordering as in the constructors (for consistency)
859  swap(first.fYAMLConfig, second.fYAMLConfig);
861  //swap(first.fHistManager, second.fHistManager); // Skip here, because the THistManager copy constructor is private.
862  //swap(first.fEmbeddingQA, second.fEmbeddingQA); // Skip here, because the THistManager copy constructor is private.
863  swap(first.fCreateQAHists, second.fCreateQAHists);
870 }
Double_t Area() const
Definition: AliEmcalJet.h:130
TObjArray fClusterCollArray
cluster collection array
bool fResponseFromThreeJetCollections
If true, the det level jets in collection 2 are only an intermediate step. They are used to get part ...
const char * title
Definition: MakeQAPdf.C:27
AliEmcalJet * ClosestJet() const
Definition: AliEmcalJet.h:341
AliJetContainer * GetJetContainer(Int_t i=0) const
std::map< std::string, std::pair< int, double ResponseMatrixFillWrapper::* > > fResponseMatrixFillMap
! Map from axis title to pair of (jet number, function to retrieve fill value)
void SetName(const char *n)
Set the name of the class of the objets inside the underlying array.
Double_t ClosestJetDistance() const
Definition: AliEmcalJet.h:342
const AliClusterIterableMomentumContainer accepted_momentum() const
Bool_t fRecycleUnusedEmbeddedEventsMode
Allows the recycling of embedded events which fail internal event selection. See the embedding helper...
void SetLeadingHadronType(Int_t t)
Double_t Phi() const
Definition: AliEmcalJet.h:117
void FillTH2(const char *hname, double x, double y, double weight=1., Option_t *opt="")
Fill a 2D histogram within the container.
double fCentrality
! Centrality of the given jet (an event level property, but useful to here available here) ...
Double_t fEPV0
!event plane V0
Declaration of class AliAnalysisTaskEmcalEmbeddingHelper.
virtual Bool_t AcceptJet(Int_t i, UInt_t &rejectionReason) const
AliJetContainer * AddJetContainer(const char *n, TString defaultCutType, Float_t jetRadius=0.4)
AliAnalysisTaskEmcalJetHPerformance & operator=(AliAnalysisTaskEmcalJetHPerformance other)
bool GetProperty(std::vector< std::string > propertyPath, const std::string &propertyName, T &property, const bool requiredProperty) const
AliEmcalEmbeddingQA fEmbeddingQA
! Embedding QA hists (will only be added if embedding).
void SetObject(TObject *const o, const char *group="/")
Set a new group into the container into the parent group.
ResponseMatrixFillWrapper CreateResponseMatrixFillWrapper(AliEmcalJet *jet) const
PWG::Tools::AliYAMLConfiguration fYAMLConfig
YAML configuration file.
bool fCreateResponseMatrix
If true, create a response matrix with the available jet collections.
Bool_t fUseBuiltinEventSelection
Use builtin event selection of the AliAnalysisTaskEmcal instead of AliEventCuts.
bool DoesConfigurationExist(const int i) const
bool AddQAPlotsToList(TList *list)
std::string fEmbeddedCellsName
Set the embedded cells collection name.
AliAnalysisTaskEmcalJetHUtils::ELeadingHadronBiasType_t fLeadingHadronBiasType
Leading hadron in jet bias type (either charged, neutral, or both)
static void ConfigureEventCuts(AliEventCuts &eventCuts, PWG::Tools::AliYAMLConfiguration &yamlConfig, const UInt_t offlineTriggerMask, const std::string &baseName, const std::string &taskName)
void FillTHnSparse(const char *name, const double *x, double weight=1., Option_t *opt="")
bool IsInitialized() const
TH2 * CreateTH2(const char *name, const char *title, int nbinsx, double xmin, double xmax, int nbinsy, double ymin, double ymax, Option_t *opt="")
Create a new TH2 within the container.
static UInt_t DeterminePhysicsSelectionFromYAML(const std::vector< std::string > &selections)
TObject * FindObject(const char *name) const
Find an object inside the container.
bool fConfigurationInitialized
True if the task configuration has been successfully initialized.
unsigned int UInt_t
Definition: External.C:33
THashList * GetListOfHistograms() const
Get the list of histograms.
Definition: THistManager.h:671
UInt_t fPreviousEventTrigger
Physics selection (offline trigger) of the previous event for determine why a small unumber of embedd...
Implementation of task to embed external events.
TString toString() const
TH1 * CreateTH1(const char *name, const char *title, int nbins, double xmin, double xmax, Option_t *opt="")
Create a new TH1 within the container.
Int_t fNcentBins
how many centrality bins
Base class for container structures within the EMCAL framework.
Double_t fCent
!event centrality
TString fCaloCellsName
name of calo cell collection
void FillTH1(const char *hname, double x, double weight=1., Option_t *opt="")
Fill a 1D histogram within the container.
static AliAnalysisTaskEmcalJetHPerformance * AddTaskEmcalJetHPerformance(const char *suffix="")
static double RelativeEPAngle(double jetAngle, double epAngle)
TObjArray fJetCollArray
jet collection array
virtual void SetNCentBins(Int_t n)
AliVCaloCells * fCaloCells
!cells
static double GetLeadingHadronPt(AliEmcalJet *jet, ELeadingHadronBiasType_t leadingHadronType)
Double_t Pt() const
Definition: AliEmcalJet.h:109
const TString & GetArrayName() const
bool fPreviousEmbeddedEventSelected
True if the previous embedded event was selected. Used to determine why a small unumber of embedded e...
const char * GetName() const
AliEventCuts fAliEventCuts
Event cuts (run2 defaults)
AliEmcalList * fOutput
!output list
void SetMakeGeneralHistograms(Bool_t g)
Enable general histograms.
Base task in the EMCAL jet framework.
Represent a jet reconstructed using the EMCal jet framework.
Definition: AliEmcalJet.h:51
Double_t GetFractionSharedPt(const AliEmcalJet *jet, AliParticleContainer *cont2=0x0) const
const char Option_t
Definition: External.C:48
void UserCreateOutputObjects()
Main initialization function on the worker.
const AliJetIterableContainer accepted() const
bool Bool_t
Definition: External.C:53
THnSparse * CreateTHnSparse(const char *name, const char *title, int ndim, const int *nbins, const double *min, const double *max, Option_t *opt="")
Create a new THnSparse within the container.
Container structure for EMCAL clusters.
void swap(PWGJE::EMCALJetTasks::AliAnalysisTaskEmcalJetHPerformance &first, PWGJE::EMCALJetTasks::AliAnalysisTaskEmcalJetHPerformance &second)
double fMinFractionShared
Minimum fraction of shared jet pt required for matching a hybrid jet to detector level.
Container for jet within the EMCAL jet framework.
static const std::map< std::string, ELeadingHadronBiasType_t > fgkLeadingHadronBiasMap
! Map from name to leading hadron bias used with the YAML config
friend std::ostream & operator<<(std::ostream &in, const AliAnalysisTaskEmcalJetHPerformance &myTask)
static const AliAnalysisTaskEmcalEmbeddingHelper * GetInstance()