Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
HFJetTruthTrigger.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file HFJetTruthTrigger.cc
1 #include "HFJetTruthTrigger.h"
2 
3 #include "HFJetDefs.h"
4 
7 #include <phool/getClass.h>
8 
10 
11 #include <g4main/PHG4Hit.h>
12 #include <g4main/PHG4Particle.h>
14 
15 #include <TDatabasePDG.h>
16 #include <TFile.h>
17 #include <TH2D.h>
18 #include <TLorentzVector.h>
19 #include <TString.h>
20 #include <TTree.h>
21 #include <g4jets/Jet.h>
22 #include <g4jets/JetMap.h>
23 #pragma GCC diagnostic push
24 #pragma GCC diagnostic ignored "-Wdeprecated-declarations"
25 #include <HepMC/GenEvent.h>
26 #include <HepMC/GenVertex.h>
29 #pragma GCC diagnostic pop
30 #include <cmath>
31 #include <cstddef>
32 #include <iostream>
33 
35  std::string jet_node, int maxevent)
36  : SubsysReco("HFJetTagger_" + jet_node)
37  , _verbose(0)
38  , _ievent(0)
39  , _total_pass(0)
40  , _f(nullptr)
41  , _h2(nullptr)
42  , _h2all(nullptr)
43  , _h2_b(nullptr)
44  , _h2_c(nullptr)
45  , _embedding_id(1)
46 {
48 
49  _flavor = flavor;
50 
51  _maxevent = maxevent;
52 
53  _pt_min = 20;
54  _pt_max = 100;
55 
56  _eta_min = -.7;
57  _eta_max = +.7;
58 
59  _jet_name = jet_node;
60 
62 }
63 
65 {
66  _verbose = true;
67 
68  _ievent = 0;
69 
70  _total_pass = 0;
71 
72  _f = new TFile(_foutname.c_str(), "RECREATE");
73 
74  _h2 = new TH2D("h2", "", 100, 0, 100.0, 40, -2, +2);
75  _h2_b = new TH2D("h2_b", "", 100, 0, 100.0, 40, -2, +2);
76  _h2_c = new TH2D("h2_c", "", 100, 0, 100.0, 40, -2, +2);
77  _h2all = new TH2D("h2all", "", 100, 0, 100.0, 40, -2, +2);
78 
79  return 0;
80 }
81 
83 {
84  PHHepMCGenEventMap* geneventmap = findNode::getClass<PHHepMCGenEventMap>(topNode, "PHHepMCGenEventMap");
85  if (!geneventmap)
86  {
87  std::cout << PHWHERE << " - Fatal error - missing node PHHepMCGenEventMap" << std::endl;
89  }
90 
91  PHHepMCGenEvent* genevt = geneventmap->get(_embedding_id);
92  if (!genevt)
93  {
94  std::cout << PHWHERE << " - Fatal error - node PHHepMCGenEventMap missing subevent with embedding ID " << _embedding_id;
95  std::cout << ". Print PHHepMCGenEventMap:";
96  geneventmap->identify();
98  }
99 
100  HepMC::GenEvent* theEvent = genevt->getEvent();
101  //theEvent->print();
102 
103  JetMap* truth_jets = findNode::getClass<JetMap>(topNode, _jet_name);
104  if (!truth_jets)
105  {
106  std::cout << PHWHERE << " - Fatal error - node " << _jet_name << " JetMap missing." << std::endl;
108  }
109  const double jet_radius = truth_jets->get_par();
110 
112  std::cout << __PRETTY_FUNCTION__ << ": truth jets has size "
113  << truth_jets->size() << " and R = " << jet_radius << std::endl;
114 
115  int ijet_t = 0;
116  bool pass_event = false;
117  for (JetMap::Iter iter = truth_jets->begin(); iter != truth_jets->end();
118  ++iter)
119  {
120  Jet* this_jet = iter->second;
121 
122  float this_pt = this_jet->get_pt();
123  float this_eta = this_jet->get_eta();
124 
125  if (this_pt < 10 || fabs(this_eta) > 5)
126  continue;
127 
128  _h2all->Fill(this_jet->get_pt(), this_eta);
129 
130  if (this_pt > _pt_min && this_pt < _pt_max && (this_eta) > _eta_min && (this_eta) < _eta_max)
131  {
132  //pass_event = true;
133  _h2->Fill(this_jet->get_pt(), this_eta);
135  this_jet->identify();
136  }
137  else
138  {
139  continue;
140  }
141 
142  const int jet_flavor = parton_tagging(this_jet, theEvent, jet_radius);
143 
144  if (abs(jet_flavor) == _flavor)
145  {
146  pass_event = true;
148  {
149  this_jet->identify();
150  std::cout << " --> this is flavor " << jet_flavor
151  << " like I want " << std::endl;
152  }
153  }
154  else
155  {
157  {
158  this_jet->identify();
159  std::cout << " --> this is flavor " << jet_flavor
160  << " which I do NOT want " << std::endl;
161  }
162  }
163 
164  hadron_tagging(this_jet, theEvent, jet_radius);
165 
166  ijet_t++;
167  }
168 
169  if (pass_event && _total_pass >= _maxevent)
170  {
172  std::cout << __PRETTY_FUNCTION__ << " --> FAIL due to max events = "
173  << _total_pass << std::endl;
174  _ievent++;
175  return _rejection_action;
176  }
177  else if (pass_event)
178  {
179  _total_pass++;
181  std::cout << __PRETTY_FUNCTION__ << " --> PASS, total = " << _total_pass
182  << std::endl;
183  _ievent++;
185  }
186  else
187  {
189  std::cout << __PRETTY_FUNCTION__ << " --> FAIL " << std::endl;
190  _ievent++;
191  return _rejection_action;
192  }
193 }
194 
196 {
198  std::cout << __PRETTY_FUNCTION__ << " DVP PASSED " << _total_pass
199  << " events" << std::endl;
200 
201  _f->cd();
202  _f->Write();
203  //_f->Close();
204 
205  return 0;
206 }
207 
209 int HFJetTruthTrigger::parton_tagging(Jet* this_jet, HepMC::GenEvent* theEvent,
210  const double match_radius)
211 {
212  float this_pt = this_jet->get_pt();
213  float this_phi = this_jet->get_phi();
214  float this_eta = this_jet->get_eta();
215 
216  int jet_flavor = 0;
217  double jet_parton_zt = 0;
218 
219  //std::cout << " truth jet #" << ijet_t << ", pt / eta / phi = " << this_pt << " / " << this_eta << " / " << this_phi << ", checking flavor" << std::endl;
220 
221  //TODO: lack taggign scheme of gluon splitting -> QQ_bar
222  for (HepMC::GenEvent::particle_const_iterator p = theEvent->particles_begin();
223  p != theEvent->particles_end(); ++p)
224  {
225  float dR = deltaR((*p)->momentum().pseudoRapidity(), this_eta,
226  (*p)->momentum().phi(), this_phi);
227  if (dR > match_radius)
228  continue;
229 
230  int pidabs = abs((*p)->pdg_id());
231  const double zt = (*p)->momentum().perp() / this_pt;
232 
233  if (pidabs == TDatabasePDG::Instance()->GetParticle("c")->PdgCode() //
234  or pidabs == TDatabasePDG::Instance()->GetParticle("b")->PdgCode() //
235  or pidabs == TDatabasePDG::Instance()->GetParticle("t")->PdgCode()) // handle heavy quarks only. All other favor tagged as default 0
236  {
237  if (pidabs > abs(jet_flavor)) // heavy quark found
238  {
239  jet_parton_zt = zt;
240  jet_flavor = (*p)->pdg_id();
241  }
242  else if (pidabs == abs(jet_flavor)) // same quark mass. next compare zt
243  {
244  if (zt > jet_parton_zt)
245  {
246  jet_parton_zt = zt;
247  jet_flavor = (*p)->pdg_id();
248  }
249  }
250 
251  if (pidabs == TDatabasePDG::Instance()->GetParticle("b")->PdgCode())
252  {
254  std::cout << __PRETTY_FUNCTION__
255  << " --BOTTOM--> pt / eta / phi = "
256  << (*p)->momentum().perp() << " / "
257  << (*p)->momentum().pseudoRapidity() << " / "
258  << (*p)->momentum().phi() << std::endl;
259  }
260  else if (pidabs == TDatabasePDG::Instance()->GetParticle("c")->PdgCode())
261  {
263  std::cout << __PRETTY_FUNCTION__
264  << " --CHARM --> pt / eta / phi = "
265  << (*p)->momentum().perp() << " / "
266  << (*p)->momentum().pseudoRapidity() << " / "
267  << (*p)->momentum().phi() << std::endl;
268  }
269  }
270  } // for (HepMC::GenEvent::particle_const_iterator p =
271 
272  if (abs(jet_flavor) == TDatabasePDG::Instance()->GetParticle("b")->PdgCode())
273  {
274  _h2_b->Fill(this_jet->get_pt(), this_eta);
275  }
276  else if (abs(jet_flavor) == TDatabasePDG::Instance()->GetParticle("c")->PdgCode())
277  {
278  _h2_c->Fill(this_jet->get_pt(), this_eta);
279  }
280 
281  this_jet->set_property(static_cast<Jet::PROPERTY>(prop_JetPartonFlavor),
282  jet_flavor);
283  this_jet->set_property(static_cast<Jet::PROPERTY>(prop_JetPartonZT),
284  jet_parton_zt);
285  // this_jet->identify();
286 
287  return jet_flavor;
288 }
289 
290 int HFJetTruthTrigger::hadron_tagging(Jet* this_jet, HepMC::GenEvent* theEvent,
291  const double match_radius)
292 {
293  float this_pt = this_jet->get_pt();
294  float this_phi = this_jet->get_phi();
295  float this_eta = this_jet->get_eta();
296 
297  int jet_flavor = 0;
298  double jet_parton_zt = 0;
299 
300  //std::cout << " truth jet #" << ijet_t << ", pt / eta / phi = " << this_pt << " / " << this_eta << " / " << this_phi << ", checking flavor" << std::endl;
301 
302  for (HepMC::GenEvent::particle_const_iterator p = theEvent->particles_begin();
303  p != theEvent->particles_end(); ++p)
304  {
305  float dR = deltaR((*p)->momentum().pseudoRapidity(), this_eta,
306  (*p)->momentum().phi(), this_phi);
307  if (dR > match_radius)
308  continue;
309 
310  int pidabs = 0;
311  TParticlePDG* pdg_p = TDatabasePDG::Instance()->GetParticle((*p)->pdg_id());
312  if (pdg_p)
313  {
314  if (TString(pdg_p->ParticleClass()).BeginsWith("B-"))
315  {
316  pidabs = TDatabasePDG::Instance()->GetParticle("b")->PdgCode();
317  }
318  else if (TString(pdg_p->ParticleClass()).BeginsWith("Charmed"))
319  {
320  pidabs = TDatabasePDG::Instance()->GetParticle("c")->PdgCode();
321  }
322  }
323 
324  const double zt = (*p)->momentum().perp() / this_pt;
325 
326  if (pidabs == TDatabasePDG::Instance()->GetParticle("c")->PdgCode() //
327  or pidabs == TDatabasePDG::Instance()->GetParticle("b")->PdgCode()) // handle heavy quarks only. All other favor tagged as default 0
328  {
329  if (pidabs > abs(jet_flavor)) // heavy quark found
330  {
331  jet_parton_zt = zt;
332  jet_flavor = pidabs;
333  }
334  else if (pidabs == abs(jet_flavor)) // same quark mass. next compare zt
335  {
336  if (zt > jet_parton_zt)
337  {
338  jet_parton_zt = zt;
339  jet_flavor = pidabs;
340  }
341  }
342 
343  if (pidabs == TDatabasePDG::Instance()->GetParticle("b")->PdgCode())
344  {
346  {
347  std::cout << __PRETTY_FUNCTION__
348  << " --BOTTOM--> pt / eta / phi = "
349  << (*p)->momentum().perp() << " / "
350  << (*p)->momentum().pseudoRapidity() << " / "
351  << (*p)->momentum().phi() << " with hadron ";
352  pdg_p->Print();
353  }
354  }
355  else if (pidabs == TDatabasePDG::Instance()->GetParticle("c")->PdgCode())
356  {
358  {
359  std::cout << __PRETTY_FUNCTION__
360  << " --CHARM --> pt / eta / phi = "
361  << (*p)->momentum().perp() << " / "
362  << (*p)->momentum().pseudoRapidity() << " / "
363  << (*p)->momentum().phi() << " with hadron ";
364  pdg_p->Print();
365  }
366  }
367  }
368  } // for (HepMC::GenEvent::particle_const_iterator p =
369 
370  this_jet->set_property(static_cast<Jet::PROPERTY>(prop_JetHadronFlavor),
371  jet_flavor);
372  this_jet->set_property(static_cast<Jet::PROPERTY>(prop_JetHadronZT),
373  jet_parton_zt);
374  // this_jet->identify();
375 
377  std::cout << __PRETTY_FUNCTION__ << " jet_flavor = " << jet_flavor
378  << std::endl;
379 
380  return jet_flavor;
381 }