CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
Qjets.cc
Go to the documentation of this file.
2 
3 using namespace std;
4 
5 void Qjets::SetRandSeed(unsigned int seed){
6  _rand_seed_set = true;
7  _seed = seed;
8 }
9 
10 bool Qjets::JetUnmerged(int num) const{
11  return _merged_jets.find(num) == _merged_jets.end();
12 }
13 
14 bool Qjets::JetsUnmerged(const JetDistance& jd) const{
15  return JetUnmerged(jd.j1) && JetUnmerged(jd.j2);
16 }
17 
19  vector< pair<JetDistance, double> > popped_distances;
20  double norm(0.);
22  ret.j1 = -1;
23  ret.j2 = -1;
24  ret.dij = -1.;
25  bool dmin_set(false);
26  double dmin(0.);
27 
28  while(!_distances.empty()){
29  JetDistance dist = _distances.top();
30  _distances.pop();
31  if(JetsUnmerged(dist)){
32  if(!dmin_set){
33  dmin = dist.dij;
34  dmin_set = true;
35  }
36  double weight = exp(-_rigidity * (dist.dij-dmin) /dmin);
37  popped_distances.push_back(make_pair(dist,weight));
38  norm += weight;
39  if(weight/norm < _truncation_fctr)
40  break;
41  }
42  }
43 
44  double rand(Rand()), tot_weight(0.);
45  for(vector<pair<JetDistance, double> >::iterator it = popped_distances.begin(); it != popped_distances.end(); it++){
46  tot_weight += (*it).second/norm;
47  if(tot_weight >= rand){
48  ret = (*it).first;
49  break;
50  }
51  }
52 
53  // repopulate in reverse (maybe quicker?)
54  for(vector<pair<JetDistance, double> >::reverse_iterator it = popped_distances.rbegin(); it != popped_distances.rend(); it++)
55  if(JetsUnmerged((*it).first))
56  _distances.push((*it).first);
57 
58  return ret;
59 }
60 
61 void Qjets::Cluster(fastjet::ClusterSequence & cs){
62  computeDCut(cs);
63 
64  // Populate all the distances
65  ComputeAllDistances(cs.jets());
66  JetDistance jd = GetNextDistance();
67 
68  while(!_distances.empty() && jd.dij != -1.){
69  if(!Prune(jd,cs)){
70  // _merged_jets.push_back(jd.j1);
71  // _merged_jets.push_back(jd.j2);
72  _merged_jets[jd.j1] = true;
73  _merged_jets[jd.j2] = true;
74 
75  int new_jet=-1;
76  cs.plugin_record_ij_recombination(jd.j1, jd.j2, 1., new_jet);
77  if(!JetUnmerged(new_jet))
78  edm::LogError("QJets Clustering") << "Problem with FastJet::plugin_record_ij_recombination";
79  ComputeNewDistanceMeasures(cs,new_jet);
80  } else {
81  double j1pt = cs.jets()[jd.j1].perp();
82  double j2pt = cs.jets()[jd.j2].perp();
83  if(j1pt>j2pt){
84  // _merged_jets.push_back(jd.j2);
85  _merged_jets[jd.j2] = true;
86  cs.plugin_record_iB_recombination(jd.j2, 1.);
87  } else {
88  // _merged_jets.push_back(jd.j1);
89  _merged_jets[jd.j1] = true;
90  cs.plugin_record_iB_recombination(jd.j1, 1.);
91  }
92  }
93  jd = GetNextDistance();
94  }
95 
96  // merge remaining jets with beam
97  int num_merged_final(0);
98  for(unsigned int i = 0 ; i < cs.jets().size(); i++)
99  if(JetUnmerged(i)){
100  num_merged_final++;
101  cs.plugin_record_iB_recombination(i,1.);
102  }
103 
104  if(!(num_merged_final < 2))
105  edm::LogError("QJets Clustering") << "More than 1 jet remains after reclustering";
106 }
107 
108 void Qjets::computeDCut(fastjet::ClusterSequence & cs){
109  // assume all jets in cs form a single jet. compute mass and pt
110  fastjet::PseudoJet sum(0.,0.,0.,0.);
111  for(vector<fastjet::PseudoJet>::const_iterator it = cs.jets().begin(); it != cs.jets().end(); it++)
112  sum += (*it);
113  _dcut = 2. * _dcut_fctr * sum.m()/sum.perp();
114 }
115 
116 bool Qjets::Prune(JetDistance& jd,fastjet::ClusterSequence & cs){
117  double pt1 = cs.jets()[jd.j1].perp();
118  double pt2 = cs.jets()[jd.j2].perp();
119  fastjet::PseudoJet sum_jet = cs.jets()[jd.j1]+cs.jets()[jd.j2];
120  double sum_pt = sum_jet.perp();
121  double z = min(pt1,pt2)/sum_pt;
122  double d2 = cs.jets()[jd.j1].plain_distance(cs.jets()[jd.j2]);
123  return (d2 > _dcut*_dcut) && (z < _zcut);
124 }
125 
126 void Qjets::ComputeAllDistances(const vector<fastjet::PseudoJet>& inp){
127  for(unsigned int i = 0 ; i < inp.size()-1; i++){
128  // jet-jet distances
129  for(unsigned int j = i+1 ; j < inp.size(); j++){
130  JetDistance jd;
131  jd.j1 = i;
132  jd.j2 = j;
133  if(jd.j1 != jd.j2){
134  jd.dij = d_ij(inp[i],inp[j]);
135  _distances.push(jd);
136  }
137  }
138  }
139 }
140 
141 void Qjets::ComputeNewDistanceMeasures(fastjet::ClusterSequence & cs, unsigned int new_jet){
142  // jet-jet distances
143  for(unsigned int i = 0; i < cs.jets().size(); i++)
144  if(JetUnmerged(i) && i != new_jet){
145  JetDistance jd;
146  jd.j1 = new_jet;
147  jd.j2 = i;
148  jd.dij = d_ij(cs.jets()[jd.j1], cs.jets()[jd.j2]);
149  _distances.push(jd);
150  }
151 }
152 
153 double Qjets::d_ij(const fastjet::PseudoJet& v1,const fastjet::PseudoJet& v2) const{
154  double p1 = v1.perp();
155  double p2 = v2.perp();
156  double ret = pow(min(p1,p2),_exp_min) * pow(max(p1,p2),_exp_max) * v1.squared_distance(v2);
157  if(edm::isNotFinite(ret))
158  edm::LogError("QJets Clustering") << "d_ij is not finite";
159  return ret;
160 }
161 
162 double Qjets::Rand(){
163  double ret = 0.;
164  //if(_rand_seed_set)
165  // ret = rand_r(&_seed)/(double)RAND_MAX;
166  //else
167  //ret = rand()/(double)RAND_MAX;
168  ret = _rnEngine->flat();
169  return ret;
170 }
void ComputeNewDistanceMeasures(fastjet::ClusterSequence &cs, unsigned int new_jet)
Definition: Qjets.cc:141
int i
Definition: DBlmapReader.cc:9
void Cluster(fastjet::ClusterSequence &cs)
Definition: Qjets.cc:61
auto_ptr< ClusterSequence > cs
bool JetUnmerged(int num) const
Definition: Qjets.cc:10
void SetRandSeed(unsigned int seed)
Definition: Qjets.cc:5
double dij
Definition: Qjets.h:15
bool Prune(JetDistance &jd, fastjet::ClusterSequence &cs)
Definition: Qjets.cc:116
int j2
Definition: Qjets.h:17
float float float z
void computeDCut(fastjet::ClusterSequence &cs)
Definition: Qjets.cc:108
JetDistance GetNextDistance()
Definition: Qjets.cc:18
bool isNotFinite(T x)
Definition: isFinite.h:10
const T & max(const T &a, const T &b)
int j
Definition: DBlmapReader.cc:9
double p2[4]
Definition: TauolaWrapper.h:90
double Rand()
Definition: Qjets.cc:162
double d_ij(const fastjet::PseudoJet &v1, const fastjet::PseudoJet &v2) const
Definition: Qjets.cc:153
void ComputeAllDistances(const std::vector< fastjet::PseudoJet > &inp)
Definition: Qjets.cc:126
double p1[4]
Definition: TauolaWrapper.h:89
Signal rand(Signal arg)
Definition: vlib.cc:442
int j1
Definition: Qjets.h:16
int weight
Definition: histoStyle.py:50
Power< A, B >::type pow(const A &a, const B &b)
Definition: Power.h:40
bool JetsUnmerged(const JetDistance &jd) const
Definition: Qjets.cc:14