ATLAS Offline Software
Qjets.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2022 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 #include "Qjets.h"
6 
7 using namespace std;
8 using namespace JetSubStructureUtils;
9 
10 Qjets::Qjets(double zcut, double dcut_fctr, double exp_min, double exp_max, double rigidity, double truncation_fctr)
11 : m_rand_seed_set(false),
12  m_zcut(zcut),
13  m_dcut(-1.),
14  m_dcut_fctr(dcut_fctr),
15  m_exp_min(exp_min),
16  m_exp_max(exp_max),
17  m_rigidity(rigidity),
18  m_truncation_fctr(truncation_fctr)
19 {
20 }
21 
22 void Qjets::SetRandSeed(unsigned int seed){
23  m_rand_seed_set = true;
24  m_seed = seed;
25 }
26 
27 bool Qjets::JetUnmerged(int num) const{
28  return m_merged_jets.find(num) == m_merged_jets.end();
29 }
30 
31 bool Qjets::JetsUnmerged(const jet_distance& jd) const{
32  return JetUnmerged(jd.j1) && JetUnmerged(jd.j2);
33 }
34 
36  vector< pair<jet_distance, double> > popped_distances;
37  double norm(0.);
38  jet_distance ret{};
39  ret.j1 = -1;
40  ret.j2 = -1;
41  ret.dij = -1.;
42  bool dmin_set(false);
43  double dmin(0.);
44 
45  while(!m_distances.empty()){
46  jet_distance dist = m_distances.top();
47  m_distances.pop();
48  if(JetsUnmerged(dist)){
49  if(!dmin_set){
50  dmin = dist.dij;
51  dmin_set = true;
52  }
53  double weight = exp(-m_rigidity * (dist.dij-dmin) /dmin);
54  popped_distances.emplace_back(dist,weight);
55  norm += weight;
57  break;
58  }
59  }
60 
61  double rand(Rand()), tot_weight(0.);
62  if (!popped_distances.empty()) {
63  const double inv_norm = 1. / norm;
64  for(vector<pair<jet_distance, double> >::iterator it = popped_distances.begin(); it != popped_distances.end(); ++it){
65  tot_weight += (*it).second * inv_norm;
66  if(tot_weight >= rand){
67  ret = (*it).first;
68  break;
69  }
70  }
71  }
72 
73  // repopulate in reverse (maybe quicker?)
74  for(vector<pair<jet_distance, double> >::reverse_iterator it = popped_distances.rbegin(); it != popped_distances.rend(); ++it)
75  if(JetsUnmerged((*it).first))
76  m_distances.push((*it).first);
77 
78  return ret;
79 }
80 
82  ComputeDCut(cs);
83 
84  // Populate all the distances
85  ComputeAllDistances(cs.jets());
87 
88  while(!m_distances.empty() && jd.dij != -1.){
89  if(!Prune(jd,cs)){
90  // m_merged_jets.push_back(jd.j1);
91  // m_merged_jets.push_back(jd.j2);
92  m_merged_jets[jd.j1] = true;
93  m_merged_jets[jd.j2] = true;
94 
95  int new_jet;
96  cs.plugin_record_ij_recombination(jd.j1, jd.j2, 1., new_jet);
97  assert(JetUnmerged(new_jet));
98  ComputeNewDistanceMeasures(cs,new_jet);
99  } else {
100  double j1pt = cs.jets()[jd.j1].perp();
101  double j2pt = cs.jets()[jd.j2].perp();
102  if(j1pt>j2pt){
103  // m_merged_jets.push_back(jd.j2);
104  m_merged_jets[jd.j2] = true;
105  cs.plugin_record_iB_recombination(jd.j2, 1.);
106  } else {
107  // m_merged_jets.push_back(jd.j1);
108  m_merged_jets[jd.j1] = true;
109  cs.plugin_record_iB_recombination(jd.j1, 1.);
110  }
111  }
112  jd = GetNextDistance();
113  }
114 
115  // merge remaining jets with beam
116  [[maybe_unused]] int num_merged_final(0);
117 
118  for(unsigned int i = 0 ; i < cs.jets().size(); i++)
119  if(JetUnmerged(i)){
120  num_merged_final++;
121  cs.plugin_record_iB_recombination(i,1.);
122  }
123 
124  assert(num_merged_final < 2);
125 }
126 
128  // assume all jets in cs form a single jet. compute mass and pt
129  fastjet::PseudoJet sum(0.,0.,0.,0.);
130  for(vector<fastjet::PseudoJet>::const_iterator it = cs.jets().begin(); it != cs.jets().end(); ++it)
131  sum += (*it);
132  m_dcut = 2. * m_dcut_fctr * sum.m()/sum.perp();
133 }
134 
136  double pt1 = cs.jets()[jd.j1].perp();
137  double pt2 = cs.jets()[jd.j2].perp();
138  fastjet::PseudoJet sum_jet = cs.jets()[jd.j1]+cs.jets()[jd.j2];
139  double sum_pt = sum_jet.perp();
140  double z = min(pt1,pt2)/sum_pt;
141  double d = sqrt(cs.jets()[jd.j1].plain_distance(cs.jets()[jd.j2]));
142  return (d > m_dcut) && (z < m_zcut);
143 }
144 
145 void Qjets::ComputeAllDistances(const vector<fastjet::PseudoJet>& inp){
146  for(unsigned int i = 0 ; i < inp.size()-1; i++){
147  // jet-jet distances
148  for(unsigned int j = i+1 ; j < inp.size(); j++){
149  jet_distance jd{};
150  jd.j1 = i;
151  jd.j2 = j;
152  if(jd.j1 != jd.j2){
153  jd.dij = d_ij(inp[i],inp[j]);
154  m_distances.push(jd);
155  }
156  }
157  }
158 }
159 
161  // jet-jet distances
162  for(unsigned int i = 0; i < cs.jets().size(); i++)
163  if(JetUnmerged(i) && ((int)i) != new_jet){
164  jet_distance jd{};
165  jd.j1 = new_jet;
166  jd.j2 = i;
167  jd.dij = d_ij(cs.jets()[jd.j1], cs.jets()[jd.j2]);
168  m_distances.push(jd);
169  }
170 }
171 
172 double Qjets::d_ij(const fastjet::PseudoJet& v1,const fastjet::PseudoJet& v2) const{
173  double p1 = v1.perp();
174  double p2 = v2.perp();
175  double ret = pow(min(p1,p2),m_exp_min) * pow(max(p1,p2),m_exp_max) * v1.squared_distance(v2);
176  assert(!std::isnan(ret));
177  return ret;
178 }
179 
180 double Qjets::Rand(){
181  double ret = 0.;
182  if(m_rand_seed_set)
183  ret = rand_r(&m_seed)/(double)RAND_MAX;
184  else
185  ret = rand()/(double)RAND_MAX;
186  return ret;
187 }
xAOD::iterator
JetConstituentVector::iterator iterator
Definition: JetConstituentVector.cxx:68
Qjets.h
JetSubStructureUtils::Qjets::m_seed
unsigned int m_seed
Definition: Qjets.h:33
JetSubStructureUtils::Qjets::m_rigidity
double m_rigidity
Definition: Qjets.h:34
PlotCalibFromCool.norm
norm
Definition: PlotCalibFromCool.py:100
max
#define max(a, b)
Definition: cfImp.cxx:41
JetSubStructureUtils::jet_distance::j2
int j2
Definition: Qjets.h:21
JetSubStructureUtils::Qjets::ComputeDCut
void ComputeDCut(fastjet::ClusterSequence &cs)
Definition: Qjets.cxx:127
hist_file_dump.d
d
Definition: hist_file_dump.py:137
JetSubStructureUtils::Qjets::m_merged_jets
std::map< int, bool > m_merged_jets
Definition: Qjets.h:35
conifer::pow
constexpr int pow(int x)
Definition: conifer.h:20
TRTCalib_cfilter.p1
p1
Definition: TRTCalib_cfilter.py:130
skel.it
it
Definition: skel.GENtoEVGEN.py:396
drawFromPickle.exp
exp
Definition: drawFromPickle.py:36
JetSubStructureUtils::Qjets::Cluster
void Cluster(fastjet::ClusterSequence &cs)
Definition: Qjets.cxx:81
JetSubStructureUtils::Qjets::d_ij
double d_ij(const fastjet::PseudoJet &v1, const fastjet::PseudoJet &v2) const
Definition: Qjets.cxx:172
JetSubStructureUtils::Qjets::Rand
double Rand()
Definition: Qjets.cxx:180
JetSubStructureUtils::Qjets::GetNextDistance
jet_distance GetNextDistance()
Definition: Qjets.cxx:35
JetSubStructureUtils
Definition: Angularity.h:10
dqt_zlumi_pandas.weight
int weight
Definition: dqt_zlumi_pandas.py:189
JetSubStructureUtils::Qjets::Prune
bool Prune(jet_distance &jd, fastjet::ClusterSequence &cs)
Definition: Qjets.cxx:135
JetSubStructureUtils::Qjets::m_dcut
double m_dcut
Definition: Qjets.h:34
python.setupRTTAlg.size
int size
Definition: setupRTTAlg.py:39
JetSubStructureUtils::Qjets::SetRandSeed
void SetRandSeed(unsigned int seed)
Definition: Qjets.cxx:22
TRTCalib_cfilter.p2
p2
Definition: TRTCalib_cfilter.py:131
convertTimingResiduals.sum
sum
Definition: convertTimingResiduals.py:55
LArG4FSStartPointFilter.rand
rand
Definition: LArG4FSStartPointFilter.py:80
jet::ClusterSequence
fastjet::ClusterSequence ClusterSequence
Definition: ClusterSequence.h:21
lumiFormat.i
int i
Definition: lumiFormat.py:85
JetSubStructureUtils::Qjets::m_exp_max
double m_exp_max
Definition: Qjets.h:34
z
#define z
JetSubStructureUtils::jet_distance
Definition: Qjets.h:18
JetSubStructureUtils::Qjets::m_zcut
double m_zcut
Definition: Qjets.h:34
JetSubStructureUtils::jet_distance::j1
int j1
Definition: Qjets.h:20
JetSubStructureUtils::Qjets::m_dcut_fctr
double m_dcut_fctr
Definition: Qjets.h:34
JetSubStructureUtils::Qjets::ComputeNewDistanceMeasures
void ComputeNewDistanceMeasures(fastjet::ClusterSequence &cs, int new_jet)
Definition: Qjets.cxx:160
xAOD::double
double
Definition: CompositeParticle_v1.cxx:159
min
#define min(a, b)
Definition: cfImp.cxx:40
trigbs_pickEvents.num
num
Definition: trigbs_pickEvents.py:76
JetSubStructureUtils::Qjets::m_truncation_fctr
double m_truncation_fctr
Definition: Qjets.h:34
JetSubStructureUtils::Qjets::m_distances
std::priority_queue< jet_distance, std::vector< jet_distance >, JetDistanceCompare > m_distances
Definition: Qjets.h:36
ReadCellNoiseFromCoolCompare.v2
v2
Definition: ReadCellNoiseFromCoolCompare.py:364
JetSubStructureUtils::Qjets::ComputeAllDistances
void ComputeAllDistances(const std::vector< fastjet::PseudoJet > &inp)
Definition: Qjets.cxx:145
JetSubStructureUtils::jet_distance::dij
double dij
Definition: Qjets.h:19
JetSubStructureUtils::Qjets::JetsUnmerged
bool JetsUnmerged(const jet_distance &jd) const
Definition: Qjets.cxx:31
JetSubStructureUtils::Qjets::JetUnmerged
bool JetUnmerged(int num) const
Definition: Qjets.cxx:27
JetSubStructureUtils::Qjets::m_rand_seed_set
bool m_rand_seed_set
Definition: Qjets.h:32
JetSubStructureUtils::Qjets::m_exp_min
double m_exp_min
Definition: Qjets.h:34