CMS 3D CMS Logo

HFClusterAlgo.cc
Go to the documentation of this file.
1 #include "HFClusterAlgo.h"
2 #include <sstream>
3 #include <iostream>
4 #include <algorithm>
5 #include <list>
9 
10 using namespace std;
11 using namespace reco;
21 {
22  m_isMC=true; // safest
23 
24 }
25 
27 public:
29  return h1.et>h2.et;
30  }
31 };
32 
34 public:
35  bool operator()(const double c1,const double c2) const {
36  return c1>c2;
37  }
38 };
39 
40 static int indexByEta(HcalDetId id) {
41  return (id.zside()>0)?(id.ietaAbs()-29+13):(41-id.ietaAbs());
42 }
43 static const double MCMaterialCorrections_3XX[] = { 1.000,1.000,1.105,0.970,0.965,0.975,0.956,0.958,0.981,1.005,0.986,1.086,1.000,
44  1.000,1.086,0.986,1.005,0.981,0.958,0.956,0.975,0.965,0.970,1.105,1.000,1.000 };
45 
46 
47 
49  bool usePMTflag,bool usePulseflag, bool forcePulseFlagMC, int correctionSet){
50  m_seedThreshold=seedThreshold;
51  m_minTowerEnergy=minTowerEnergy;
52  m_maximumSL=maximumSL;
53  m_usePMTFlag=usePMTflag;
54  m_usePulseFlag=usePulseflag;
55  m_forcePulseFlagMC=forcePulseFlagMC;
56  m_maximumRenergy=maximumRenergy;
57  m_correctionSet = correctionSet;
58 
59  for(int ii=0;ii<13;ii++){
60  m_cutByEta.push_back(-1);
61  m_seedmnEta.push_back(99);
62  m_seedMXeta.push_back(-1);
63  }
64  for(int ii=0;ii<73;ii++){
65  double minphi=0.0872664*(ii-1);
66  double maxphi=0.0872664*(ii+1);
67  while (minphi < -M_PI)
68  minphi+=2*M_PI;
69  while (minphi > M_PI)
70  minphi-=2*M_PI;
71  while (maxphi < -M_PI)
72  maxphi+=2*M_PI;
73  while (maxphi > M_PI)
74  maxphi-=2*M_PI;
75  if(ii==37)
76  minphi=-3.1415904;
77  m_seedmnPhi.push_back(minphi);
78  m_seedMXphi.push_back(maxphi);
79  }
80 
81  // always set all the corrections to one...
82  for (int ii=0; ii<13*2; ii++)
83  m_correctionByEta.push_back(1.0);
84  if (m_correctionSet==1) { // corrections for material from MC
85  for (int ii=0; ii<13*2; ii++)
86  m_correctionByEta[ii]=MCMaterialCorrections_3XX[ii];
87  }
88 }
89 
92  const CaloGeometry& geomO,
94  SuperClusterCollection& SuperClusters) {
95 
96  const CaloGeometry* geom(&geomO);
97  std::vector<HFCompleteHit> protoseeds, seeds;
99  std::vector<HFCompleteHit>::iterator i;
100  std::vector<HFCompleteHit>::iterator k;
101  int dP, dE, PWrap;
102  bool isok=true;
103  HFEMClusterShape clusShp;
104 
105  SuperCluster Sclus;
106  bool doCluster=false;
107 
108  for (j=hf.begin(); j!= hf.end(); j++) {
109  const int aieta=j->id().ietaAbs();
110  int iz=(aieta-29);
111  // only long fibers and not 29,40,41 allowed to be considered as seeds
112  if (j->id().depth()!=1) continue;
113  if (aieta==40 || aieta==41 || aieta==29) continue;
114 
115 
116  if (iz<0 || iz>12) {
117  edm::LogWarning("HFClusterAlgo") << "Strange invalid HF hit: " << j->id();
118  continue;
119  }
120 
121  if (m_cutByEta[iz]<0) {
122  double eta=geom->getPosition(j->id()).eta();
123  m_cutByEta[iz]=m_seedThreshold*cosh(eta); // convert ET to E for this ring
124  auto ccg=geom->getGeometry(j->id());
125  const CaloCellGeometry::CornersVec& CellCorners=ccg->getCorners();
126  for(size_t sc=0;sc<CellCorners.size();sc++){
127  if(fabs(CellCorners[sc].z())<1200){
128  if(fabs(CellCorners[sc].eta())<m_seedmnEta[iz])m_seedmnEta[iz]=fabs(CellCorners[sc].eta());
129  if(fabs(CellCorners[sc].eta())>m_seedMXeta[iz])m_seedMXeta[iz]=fabs(CellCorners[sc].eta());
130  }
131  }
132  }
133  double elong=j->energy()*m_correctionByEta[indexByEta(j->id())];
134  if (elong>m_cutByEta[iz]) {
135  j2=hf.find(HcalDetId(HcalForward,j->id().ieta(),j->id().iphi(),2));
136  double eshort=(j2==hf.end())?(0):(j2->energy());
137  if (j2!=hf.end())
138  eshort*=m_correctionByEta[indexByEta(j2->id())];
139  if (((elong-eshort)/(elong+eshort))>m_maximumSL) continue;
140  //if ((m_usePMTFlag)&&(j->flagField(4,1))) continue;
141  //if ((m_usePulseFlag)&&(j->flagField(1,1))) continue;
142  if(isPMTHit(*j)) continue;
143 
144  HFCompleteHit ahit;
145  double eta=geom->getPosition(j->id()).eta();
146  ahit.id=j->id();
147  ahit.energy=elong;
148  ahit.et=ahit.energy/cosh(eta);
149  protoseeds.push_back(ahit);
150  }
151  }
152 
153  if(!protoseeds.empty()){
154  std::sort(protoseeds.begin(), protoseeds.end(), CompareHFCompleteHitET());
155  for (i=protoseeds.begin(); i!= protoseeds.end(); i++) {
156  isok=true;
157  doCluster=false;
158 
159  if ( (i==protoseeds.begin()) && (isok) ) {
160  doCluster=true;
161  }else {
162  // check for overlap with existing clusters
163  for (k=seeds.begin(); isok && k!=seeds.end(); k++) { //i->hits, k->seeds
164 
165  for (dE=-2; dE<=2; dE++)
166  for (dP=-4;dP<=4; dP+=2) {
167  PWrap=k->id.iphi()+dP;
168  if (PWrap<0)
169  PWrap+=72;
170  if (PWrap>72)
171  PWrap-=72;
172 
173  if ( (i->id.iphi()==PWrap) && (i->id.ieta()==k->id.ieta()+dE))
174  isok = false;
175  }
176  }
177  if (isok) {
178  doCluster=true;
179  }
180  }
181  if (doCluster) {
182  seeds.push_back(*i);
183 
184  bool clusterOk=makeCluster( i->id(),hf, geom,clusShp,Sclus);
185  if (clusterOk) { // cluster is _not_ ok if seed is rejected due to other cuts
186  clusterShapes.push_back(clusShp);
187  SuperClusters.push_back(Sclus);
188  }
189 
190  }
191  }//end protoseed loop
192  }//end if seeCount
193 }
194 
195 
197  const HFRecHitCollection& hf,
198  const CaloGeometry* geom,
199  HFEMClusterShape& clusShp,
200  SuperCluster& Sclus) {
201 
202 
203  double w=0;//sum over all log E's
204  double wgt=0;
205  double w_e=0;//sum over ieat*energy
206  double w_x=0;
207  double w_y=0;
208  double w_z=0;
209  double wp_e=0;//sum over iphi*energy
210  double e_e=0;//nonwieghted eta sum
211  double e_ep=0; //nonweighted phi sum
212 
213  double l_3=0;//sum for enenergy in 3x3 long fibers etc.
214  double s_3=0;
215  double l_5=0;
216  double s_5=0;
217  double l_1=0;
218  double s_1=0;
219  int de, dp, phiWrap;
220  double l_1e=0;
221  const GlobalPoint& sp=geom->getPosition(seedid);
222  std::vector<double> coreCanid;
223  std::vector<double>::const_iterator ci;
225  std::vector<DetId> usedHits;
226 
228  HcalDetId sid(HcalForward,seedid.ieta(),seedid.iphi(),1);
229  si=hf.find(sid);
230 
231  bool clusterOk=true; // assume the best to start...
232 
233  // lots happens here
234  // edge type 1 has 40/41 in 3x3 and 5x5
235  bool edge_type1=seedid.ietaAbs()==39 && (seedid.iphi()%4)==3;
236 
237  double e_seed=si->energy()*m_correctionByEta[indexByEta(si->id())];
238 
239  for (de=-2; de<=2; de++)
240  for (dp=-4;dp<=4; dp+=2) {
241  phiWrap=seedid.iphi()+dp;
242  if (phiWrap<0)
243  phiWrap+=72;
244  if (phiWrap>72)
245  phiWrap-=72;
246 
247 
248  /* Handling of phi-width change problems */
249  if (edge_type1 && de==seedid.zside()) {
250  if (dp==-2) { // we want it in the 3x3
251  phiWrap-=2;
252  if (phiWrap<0)
253  phiWrap+=72;
254  }
255  else if (dp==-4) {
256  continue; // but not double counted in 5x5
257  }
258  }
259 
260  HcalDetId idl(HcalForward,seedid.ieta()+de,phiWrap,1);
261  HcalDetId ids(HcalForward,seedid.ieta()+de,phiWrap,2);
262 
263 
264  il=hf.find(idl);
265  is=hf.find(ids);
266 
267 
268 
269 
270  double e_long=1.0;
271  double e_short=0.0;
272  if (il!=hf.end()) e_long=il->energy()*m_correctionByEta[indexByEta(il->id())];
273  if (e_long <= m_minTowerEnergy) e_long=0.0;
274  if (is!=hf.end()) e_short=is->energy()*m_correctionByEta[indexByEta(is->id())];
275  if (e_short <= m_minTowerEnergy) e_short=0.0;
276  double eRatio=(e_long-e_short)/std::max(1.0,(e_long+e_short));
277 
278  // require S/L > a minimum amount for inclusion
279  if ((abs(eRatio) > m_maximumSL)&&(std::max(e_long,e_short) > m_maximumRenergy)) {
280  if (dp==0 && de==0) clusterOk=false; // somehow, the seed is hosed
281  continue;
282  }
283 
284  if((il!=hf.end())&&(isPMTHit(*il))){
285  if (dp==0 && de==0) clusterOk=false; // somehow, the seed is hosed
286  continue;//continue to next hit, do not include this one in cluster
287  }
288 
289 
290 
291 
292 
293  if (e_long > m_minTowerEnergy && il!=hf.end()) {
294 
295  // record usage
296  usedHits.push_back(idl.rawId());
297  // always in the 5x5
298  l_5+=e_long;
299  // maybe in the 3x3
300  if ((de>-2)&&(de<2)&&(dp>-4)&&(dp<4)) {
301  l_3+=e_long;
302 
303  // sometimes in the 1x1
304  if ((dp==0)&&(de==0)) {
305  l_1=e_long;
306  }
307 
308  // maybe in the core?
309  if ((de>-2)&&(de<2)&&(dp>-4)&&(dp<4)&&(e_long>(.5*e_seed))) {
310  coreCanid.push_back(e_long);
311  }
312 
313  // position calculation
314  const GlobalPoint& p=geom->getPosition(idl);
315 
316  double d_p = p.phi()-sp.phi();
317  while (d_p < -M_PI)
318  d_p+=2*M_PI;
319  while (d_p > M_PI)
320  d_p-=2*M_PI;
321  double d_e = p.eta()-sp.eta();
322 
323  wgt=log((e_long));
324  if (wgt>0){
325  w+=wgt;
326  w_e+=(d_e)*wgt;
327  wp_e+=(d_p)*wgt;
328  e_e+=d_e;
329  e_ep+=d_p;
330 
331  w_x+=(p.x())*wgt;//(p.x()-sp.x())*wgt;
332  w_y+=(p.y())*wgt;
333  w_z+=(p.z())*wgt;
334  }
335  }
336  } else {
337  if (dp==0 && de==0) clusterOk=false; // somehow, the seed is hosed
338  }
339 
340  if (e_short > m_minTowerEnergy && is!=hf.end()) {
341  // record usage
342  usedHits.push_back(ids.rawId());
343  // always in the 5x5
344  s_5+=e_short;
345  // maybe in the 3x3
346  if ((de>-2)&&(de<2)&&(dp>-4)&&(dp<4)) {
347  s_3+=e_short;
348  }
349  // sometimes in the 1x1
350  if ((dp==0)&&(de==0)) {
351  s_1=e_short;
352  }
353  }
354  }
355 
356 
357  if (!clusterOk) return false;
358 
359  //Core sorting done here
360  std::sort(coreCanid.begin(), coreCanid.end(), CompareHFCore());
361  for (ci=coreCanid.begin();ci!=coreCanid.end();ci++){
362  if(ci==coreCanid.begin()){
363  l_1e=*ci;
364  }else if (*ci>.5*l_1e){
365  l_1e+=*ci;
366  }
367  }//core sorting end
368 
369  double z_=w_z/w;
370  double x_=w_x/w;
371  double y_=w_y/w;
372  math::XYZPoint xyzclus(x_,y_,z_);
373  //calcualte position, final
374  double eta=xyzclus.eta();//w_e/w+sp.eta();
375 
376  double phi=xyzclus.phi();//(wp_e/w)+sp.phi();
377 
378  while (phi < -M_PI)
379  phi+=2*M_PI;
380  while (phi > M_PI)
381  phi-=2*M_PI;
382 
383  //calculate cell phi and cell eta
384  int idx= fabs(seedid.ieta())-29;
385  int ipx=seedid.iphi();
386  double Cphi =(phi-m_seedmnPhi[ipx])/(m_seedMXphi[ipx]-m_seedmnPhi[ipx]);
387  double Ceta=(fabs(eta)- m_seedmnEta[idx])/(m_seedMXeta[idx]-m_seedmnEta[idx]);
388 
389  //return HFEMClusterShape, SuperCluster
390  HFEMClusterShape myClusShp(l_1, s_1, l_3, s_3, l_5,s_5, l_1e,Ceta, Cphi,seedid);
391  clusShp = myClusShp;
392 
393  SuperCluster MySclus(l_3,xyzclus);
394  Sclus=MySclus;
395 
396  return clusterOk;
397 
398 }
400 
401  bool pmthit=false;
402 
403  if((hfr.flagField(HcalCaloFlagLabels::HFLongShort))&&(m_usePMTFlag)) pmthit=true;
404  if (!(m_isMC && !m_forcePulseFlagMC))
405  if((hfr.flagField(HcalCaloFlagLabels::HFDigiTime))&&(m_usePulseFlag)) pmthit=true;
406 
407  return pmthit;
408 }
410  edm::LogInfo("HFClusterAlgo")<<"Resetting for Run!";
411  for(int ii=0;ii<13;ii++){
412  m_cutByEta.push_back(-1);
413  m_seedmnEta.push_back(99);
414  m_seedMXeta.push_back(-1);
415  }
416 }
417 
void clusterize(const HFRecHitCollection &hf, const CaloGeometry &geom, reco::HFEMClusterShapeCollection &clusters, reco::SuperClusterCollection &SuperClusters)
const double w
Definition: UKUtility.cc:23
int zside() const
get the z-side of the cell (1/-1)
Definition: HcalDetId.h:145
Geom::Phi< T > phi() const
Definition: PV3DBase.h:69
std::vector< HFRecHit >::const_iterator const_iterator
T y() const
Definition: PV3DBase.h:63
int zside(DetId const &)
std::vector< HFEMClusterShape > HFEMClusterShapeCollection
l1t::ClusterShapes clusterShapes
Definition: classes.h:57
static const double MCMaterialCorrections_3XX[]
bool operator()(const HFClusterAlgo::HFCompleteHit &h1, const HFClusterAlgo::HFCompleteHit &h2) const
std::vector< SuperCluster > SuperClusterCollection
collection of SuperCluser objectr
T z() const
Definition: PV3DBase.h:64
int ieta() const
get the cell ieta
Definition: HcalDetId.h:155
GlobalPoint getPosition(const DetId &id) const
Get the position of a given detector id.
Definition: CaloGeometry.cc:74
Abs< T >::type abs(const T &t)
Definition: Abs.h:22
ii
Definition: cuy.py:589
#define M_PI
int k[5][pyjets_maxn]
int ietaAbs() const
get the absolute value of the cell ieta
Definition: HcalDetId.h:150
const_iterator end() const
static int indexByEta(HcalDetId id)
int iphi() const
get the cell iphi
Definition: HcalDetId.h:157
size_type size() const
Definition: EZArrayFL.h:81
constexpr uint32_t flagField(int base, int width=1) const
Definition: CaloRecHit.h:48
bool operator()(const double c1, const double c2) const
XYZPointD XYZPoint
point in space with cartesian internal representation
Definition: Point3D.h:12
T eta() const
Definition: PV3DBase.h:76
iterator find(key_type k)
fixed size matrix
std::shared_ptr< const CaloCellGeometry > getGeometry(const DetId &id) const
Get the cell geometry of a given detector id.
Definition: CaloGeometry.cc:85
bool makeCluster(const HcalDetId &seedid, const HFRecHitCollection &hf, const CaloGeometry *geom, reco::HFEMClusterShape &clusShp, reco::SuperCluster &SClus)
T x() const
Definition: PV3DBase.h:62
bool isPMTHit(const HFRecHit &hfr)
void setup(double minTowerEnergy, double seedThreshold, double maximumSL, double m_maximumRenergy, bool usePMTflag, bool usePulseflag, bool forcePulseFlagMC, int correctionSet)
const_iterator begin() const