CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
L1GtMuonCondition.cc
Go to the documentation of this file.
1 
17 // this class header
19 
20 // system include files
21 #include <iostream>
22 #include <iomanip>
23 
24 #include <string>
25 #include <vector>
26 #include <algorithm>
27 
28 // user include files
29 // base classes
32 
34 
36 
39 
42 
43 // constructors
44 // default
47 
48  // empty
49 
50 }
51 
52 // from base template condition (from event setup usually)
54  const L1GlobalTriggerGTL* ptrGTL, const int nrL1Mu,
55  const int ifMuEtaNumberBits) :
57  m_gtMuonTemplate(static_cast<const L1GtMuonTemplate*>(muonTemplate)),
58  m_gtGTL(ptrGTL),
59  m_ifMuEtaNumberBits(ifMuEtaNumberBits)
60 {
62  m_condMaxNumberObjects = nrL1Mu;
63 }
64 
65 // copy constructor
67 
69  m_gtGTL = cp.gtGTL();
70 
73 
77 
79 
80 }
81 
84  copy(cp);
85 }
86 
87 // destructor
89 
90  // empty
91 
92 }
93 
94 // equal operator
96 {
97  copy(cp);
98  return *this;
99 }
100 
101 // methods
103 
104  m_gtMuonTemplate = muonTempl;
105 
106 }
107 
110 
111  m_gtGTL = ptrGTL;
112 
113 }
114 
115 
116 // set the number of bits for eta of muon objects
118  const int& ifMuEtaNumberBitsValue) {
119 
120  m_ifMuEtaNumberBits = ifMuEtaNumberBitsValue;
121 
122 }
123 
124 // set the maximum number of bins for the delta phi scales
126  const int& corrParDeltaPhiNrBins) {
127 
128  m_corrParDeltaPhiNrBins = corrParDeltaPhiNrBins;
129 
130 }
131 
132 
133 // try all object permutations and check spatial correlations, if required
135 
136  // number of trigger objects in the condition
137  int nObjInCond = m_gtMuonTemplate->nrObjects();
138 
139  // the candidates
140  const std::vector<const L1MuGMTCand*>* candVec = m_gtGTL->getCandL1Mu();
141 
142  int numberObjects = candVec->size();
143  //LogTrace("L1GlobalTrigger") << " numberObjects: " << numberObjects
144  // << std::endl;
145  if (numberObjects < nObjInCond) {
146  return false;
147  }
148 
149  std::vector<int> index(numberObjects);
150 
151  for (int i = 0; i < numberObjects; ++i) {
152  index[i] = i;
153  }
154 
155  int jumpIndex = 1;
156  int jump = factorial(numberObjects - nObjInCond);
157 
158  int totalLoops = 0;
159  int passLoops = 0;
160 
161  // condition result condResult set to true if at least one permutation
162  // passes all requirements
163  // all possible permutations are checked
164  bool condResult = false;
165 
166  // store the indices of the muon objects
167  // from the combination evaluated in the condition
168  SingleCombInCond objectsInComb;
169  objectsInComb.reserve(nObjInCond);
170 
171  // clear the m_combinationsInCond vector
173 
174  do {
175 
176  if (--jumpIndex)
177  continue;
178 
179  jumpIndex = jump;
180  totalLoops++;
181 
182  // clear the indices in the combination
183  objectsInComb.clear();
184 
185  bool tmpResult = true;
186 
187  // check if there is a permutation that matches object-parameter requirements
188  for (int i = 0; i < nObjInCond; i++) {
189 
190  tmpResult &= checkObjectParameter(i, *(*candVec)[index[i]]);
191  objectsInComb.push_back(index[i]);
192 
193  }
194 
195  // if permutation does not match particle conditions
196  // skip charge correlation and spatial correlations
197  if ( !tmpResult) {
198 
199  continue;
200 
201  }
202 
203  // get the correlation parameters (chargeCorrelation included here also)
206 
207  // charge_correlation consists of 3 relevant bits (D2, D1, D0)
208  unsigned int chargeCorr = corrPar.chargeCorrelation;
209 
210  // charge ignore bit (D0) not set?
211  if ((chargeCorr & 1) == 0) {
212 
213  for (int i = 0; i < nObjInCond; i++) {
214  // check valid charge - skip if invalid charge
215  bool chargeValid = (*candVec)[index[i]]->charge_valid();
216  tmpResult &= chargeValid;
217 
218  if ( !chargeValid) {
219  continue;
220  }
221  }
222 
223  if ( !tmpResult) {
224  continue;
225  }
226 
227  if (nObjInCond == 1) { // one object condition
228 
229  // D2..enable pos, D1..enable neg
230  if ( ! ( ( (chargeCorr & 4) != 0 && (*candVec)[index[0]]->charge()> 0 )
231  || ( (chargeCorr & 2) != 0 && (*candVec)[index[0]]->charge() < 0 ) )) {
232 
233  continue;
234  }
235 
236  }
237  else { // more objects condition
238 
239  // find out if signs are equal
240  bool equalSigns = true;
241  for (int i = 0; i < nObjInCond-1; i++) {
242  if ((*candVec)[index[i]]->charge() != (*candVec)[index[i+1]]->charge()) {
243  equalSigns = false;
244  break;
245  }
246  }
247 
248  // two or three particle condition
249  if (nObjInCond == 2 || nObjInCond == 3) {
250  // D2..enable equal, D1..enable not equal
251  if ( ! ( ( (chargeCorr & 4) != 0 && equalSigns ) || ( (chargeCorr & 2) != 0
252  && !equalSigns ) )) {
253 
254  continue;
255  }
256  }
257 
258  // four particle condition
259  if (nObjInCond == 4) {
260  //counter to count positive charges to determine if there are pairs
261  unsigned int posCount = 0;
262 
263  for (int i = 0; i < nObjInCond; i++) {
264  if ((*candVec)[index[i]]->charge()> 0) {
265  posCount++;
266  }
267  }
268 
269  // D2..enable equal, D1..enable pairs
270  if ( ! ( ( (chargeCorr & 4) != 0 && equalSigns ) || ( (chargeCorr & 2) != 0
271  && posCount == 2 ) )) {
272 
273  continue;
274  }
275  }
276  }
277  } // end signchecks
278 
279 
280  if (m_gtMuonTemplate->wsc()) {
281 
282  // wsc requirements have always nObjInCond = 2
283  // one can use directly index[0] and index[1] to compute
284  // eta and phi differences
285  const int ObjInWscComb = 2;
286  if (nObjInCond != ObjInWscComb) {
287 
288  edm::LogError("L1GlobalTrigger") << "\n Error: "
289  << "number of particles in condition with spatial correlation = " << nObjInCond
290  << "\n it must be = " << ObjInWscComb << std::endl;
291  // TODO Perhaps I should throw here an exception,
292  // since something is really wrong if nObjInCond != ObjInWscComb (=2)
293  continue;
294  }
295 
296  unsigned int candDeltaEta;
297  unsigned int candDeltaPhi;
298 
299  // check candDeltaEta
300 
301  // get eta index and the sign bit of the eta index (MSB is the sign)
302  // signedEta[i] is the signed eta index of (*candVec)[index[i]]
303  int signedEta[ObjInWscComb];
304  int signBit[ObjInWscComb] = { 0, 0 };
305 
306  int scaleEta = 1 << (m_ifMuEtaNumberBits - 1);
307 
308  for (int i = 0; i < ObjInWscComb; ++i) {
309  signBit[i] = ((*candVec)[index[i]]->etaIndex() & scaleEta)>>(m_ifMuEtaNumberBits - 1);
310  signedEta[i] = ((*candVec)[index[i]]->etaIndex() )%scaleEta;
311 
312  if (signBit[i] == 1) {
313  signedEta[i] = (-1)*signedEta[i];
314  }
315 
316  }
317 
318  // compute candDeltaEta - add 1 if signs are different (due to +0/-0 indices)
319  candDeltaEta = static_cast<int> (std::abs(signedEta[1] - signedEta[0]))
320  + static_cast<int> (signBit[1]^signBit[0]);
321 
322  if ( !checkBit(corrPar.deltaEtaRange, candDeltaEta) ) {
323  continue;
324  }
325 
326  // check candDeltaPhi
327 
328  // calculate absolute value of candDeltaPhi
329  if ((*candVec)[index[0]]->phiIndex()> (*candVec)[index[1]]->phiIndex()) {
330  candDeltaPhi = (*candVec)[index[0]]->phiIndex() - (*candVec)[index[1]]->phiIndex();
331  }
332  else {
333  candDeltaPhi = (*candVec)[index[1]]->phiIndex() - (*candVec)[index[0]]->phiIndex();
334  }
335 
336  // check if candDeltaPhi > 180 (via delta_phi_maxbits)
337  // delta_phi contains bits for 0..180 (0 and 180 included)
338  // protect also against infinite loop...
339 
340  int nMaxLoop = 10;
341  int iLoop = 0;
342 
343  while (candDeltaPhi >= m_corrParDeltaPhiNrBins) {
344 
345  unsigned int candDeltaPhiInitial = candDeltaPhi;
346 
347  // candDeltaPhi > 180 ==> take 360 - candDeltaPhi
348  candDeltaPhi = (m_corrParDeltaPhiNrBins - 1) * 2 - candDeltaPhi;
349  if (m_verbosity) {
350  LogTrace("L1GlobalTrigger")
351  << " Initial candDeltaPhi = "
352  << candDeltaPhiInitial
353  << " > m_corrParDeltaPhiNrBins = "
355  << " ==> candDeltaPhi rescaled to: "
356  << candDeltaPhi << " [ loop index " << iLoop
357  << "; breaks after " << nMaxLoop << " loops ]\n"
358  << std::endl;
359  }
360 
361  iLoop++;
362  if (iLoop > nMaxLoop) {
363  return false;
364  }
365  }
366 
367  // delta_phi bitmask is saved in two boost::uint64_t words
368  if (candDeltaPhi < 64) {
369  if (!checkBit(corrPar.deltaPhiRange0Word, candDeltaPhi) ) {
370  continue;
371  }
372  }
373  else {
374  if (!checkBit(corrPar.deltaPhiRange1Word, (candDeltaPhi - 64))) {
375  continue;
376  }
377  }
378 
379  } // end wsc check
380 
381  // if we get here all checks were successfull for this combination
382  // set the general result for evaluateCondition to "true"
383 
384  condResult = true;
385  passLoops++;
386  (combinationsInCond()).push_back(objectsInComb);
387 
388  } while (std::next_permutation(index.begin(), index.end()) );
389 
390  //LogTrace("L1GlobalTrigger")
391  // << "\n L1GtMuonCondition: total number of permutations found: " << totalLoops
392  // << "\n L1GtMuonCondition: number of permutations passing requirements: " << passLoops
393  // << "\n" << std::endl;
394 
395  return condResult;
396 
397 }
398 
399 // load muon candidates
400 const L1MuGMTCand* L1GtMuonCondition::getCandidate(const int indexCand) const {
401 
402  return (*(m_gtGTL->getCandL1Mu()))[indexCand];
403 }
404 
414 const bool L1GtMuonCondition::checkObjectParameter(const int iCondition, const L1MuGMTCand& cand) const {
415 
416  // number of objects in condition
417  int nObjInCond = m_gtMuonTemplate->nrObjects();
418 
419  if (iCondition >= nObjInCond || iCondition < 0) {
420  return false;
421  }
422 
423  // empty candidates can not be compared
424  if (cand.empty()) {
425  return false;
426  }
427 
428  const L1GtMuonTemplate::ObjectParameter objPar =
429  ( *(m_gtMuonTemplate->objectParameter()) )[iCondition];
430 
431  // using the logic table from GTL-9U-module.pdf
432  // "Truth table for Isolation bit"
433 
434  // check thresholds:
435 
436  // value < low pt threshold
437  // fail trigger
438 
439  // low pt threshold <= value < high pt threshold & non-isolated muon:
440  // requestIso true: fail trigger
441  // requestIso false, enableIso true: fail trigger
442  // requestIso false, enableIso false: OK, trigger
443 
444  // low pt threshold <= value < high pt threshold & isolated muon:
445  // requestIso true: OK, trigger
446  // requestIso false, enableIso true: OK, trigger
447  // requestIso false, enableIso false: OK, trigger
448 
449  // value >= high pt threshold & non-isolated muon:
450  // requestIso true: fail trigger
451  // requestIso false: OK, trigger
452 
453  // value >= high pt threshold & isolated muon:
454  // OK, trigger
455 
456 
457  if ( !checkThreshold(objPar.ptHighThreshold, cand.ptIndex(), m_gtMuonTemplate->condGEq()) ) {
458 
459  if ( !checkThreshold(objPar.ptLowThreshold, cand.ptIndex(), m_gtMuonTemplate->condGEq()) ) {
460 
461  return false;
462  }
463  else {
464 
465  // check isolation
466  if ( !cand.isol() ) {
467  if (objPar.requestIso || objPar.enableIso) {
468 
469  return false;
470  }
471  }
472 
473  }
474 
475  }
476  else {
477 
478  if ( !cand.isol() ) {
479  if (objPar.requestIso) {
480 
481  return false;
482  }
483  }
484 
485  }
486 
487  // check eta
488 
489  if (!checkBit(objPar.etaRange, cand.etaIndex())) {
490  return false;
491  }
492 
493  // check phi - in the requested range (no LUT used - LUT too big for hw chip)
494  // for phiLow <= phiHigh takes [phiLow, phiHigh]
495  // for phiLow >= phiHigh takes [phiLow, phiHigh] over zero angle!
496 
497  if (objPar.phiHigh >= objPar.phiLow) {
498 
499  if (! ( (objPar.phiLow <= cand.phiIndex()) && (cand.phiIndex() <= objPar.phiHigh ) )) {
500 
501  return false;
502  }
503 
504  }
505  else { // go over zero angle!!
506  if (! ( (objPar.phiLow <= cand.phiIndex()) || (cand.phiIndex() <= objPar.phiHigh ) )) {
507 
508  return false;
509  }
510  }
511 
512  // check quality ( bit check )
513 
514  // A number of values is required to trigger (at least one).
515  // "Don’t care" means that all values are allowed.
516  // Qual = 000 means then NO MUON (GTL module)
517 
518  if (cand.quality() == 0) {
519  return false;
520  }
521 
522  if (objPar.qualityRange == 0) {
523  return false;
524  }
525  else {
526  if (!checkBit(objPar.qualityRange, cand.quality())) {
527  return false;
528  }
529  }
530 
531  // check mip
532  if (objPar.enableMip) {
533  if (!cand.mip()) {
534 
535  return false;
536  }
537  }
538 
539  // particle matches if we get here
540  //LogTrace("L1GlobalTrigger")
541  // << " checkObjectParameter: muon object OK, passes all requirements\n" << std::endl;
542 
543  return true;
544 }
545 
546 void L1GtMuonCondition::print(std::ostream& myCout) const {
547 
548  m_gtMuonTemplate->print(myCout);
549 
550  myCout << " Number of bits for eta of muon objects = "
551  << m_ifMuEtaNumberBits << std::endl;
552  myCout << " Maximum number of bins for the delta phi scales = "
553  << m_corrParDeltaPhiNrBins << "\n " << std::endl;
554 
556 
557 }
558 
L1GtMuonCondition & operator=(const L1GtMuonCondition &)
int i
Definition: DBlmapReader.cc:9
const int nrObjects() const
get number of trigger objects
const CorrelationParameter * correlationParameter() const
const bool checkBit(const Type1 &mask, const unsigned int bitNumber) const
check if a bit with a given number is set in a mask
virtual ~L1GtMuonCondition()
bool m_condLastResult
the last result of evaluateCondition()
unsigned int phiIndex() const
get phi-code
Definition: L1MuGMTCand.h:75
CombinationsInCond m_combinationsInCond
store all the object combinations evaluated to true in the condition
CombinationsInCond & combinationsInCond() const
get all the object combinations (to fill it...)
void setGtIfMuEtaNumberBits(const int &)
unsigned int m_corrParDeltaPhiNrBins
#define abs(x)
Definition: mlp_lapack.h:159
unsigned int etaIndex() const
get eta-code
Definition: L1MuGMTCand.h:110
void copy(const L1GtMuonCondition &cp)
copy function for copy constructor and operator=
std::vector< int > SingleCombInCond
typedefs
int m_ifMuEtaNumberBits
number of bits for eta of muon objects
const L1GtMuonTemplate * m_gtMuonTemplate
pointer to a L1GtMuonTemplate
double charge(const std::vector< uint8_t > &Ampls)
bool isol() const
get isolation
Definition: L1MuGMTCand.h:116
const int gtIfMuEtaNumberBits() const
get / set the number of bits for eta of muon objects
bool empty() const
is it an empty muon candidate?
Definition: L1MuGMTCand.h:66
const bool wsc() const
void clear(CLHEP::HepGenMatrix &m)
Helper function: Reset all elements of a matrix to 0.
Definition: matutil.cc:168
const bool checkThreshold(const Type1 &threshold, const Type2 &value, const bool condGEqValue) const
const L1MuGMTCand * getCandidate(const int indexCand) const
load muon candidates
const L1GlobalTriggerGTL * gtGTL() const
get / set the pointer to GTL
const std::vector< ObjectParameter > * objectParameter() const
bool mip() const
get mip
Definition: L1MuGMTCand.h:119
const bool checkObjectParameter(const int iCondition, const L1MuGMTCand &cand) const
function to check a single object if it matches a condition
#define LogTrace(id)
void setGtGTL(const L1GlobalTriggerGTL *)
set the pointer to GTL
unsigned int quality() const
get quality
Definition: L1MuGMTCand.h:95
void setGtMuonTemplate(const L1GtMuonTemplate *)
const bool evaluateCondition() const
the core function to check if the condition matches
const L1GlobalTriggerGTL * m_gtGTL
pointer to GTL, to be able to get the trigger objects
virtual void print(std::ostream &myCout) const
print the condition
string const
Definition: compareJSON.py:14
const L1GtMuonTemplate * gtMuonTemplate() const
get / set the pointer to a L1GtCondition
void print(std::ostream &myCout) const
print condition
void setGtCorrParDeltaPhiNrBins(const int &)
int factorial(int n)
factorial function
virtual void print(std::ostream &myCout) const
print condition
const bool condGEq() const
get / set condition GEq flag
Definition: L1GtCondition.h:99
const std::vector< const L1MuGMTCand * > * getCandL1Mu() const
return global muon trigger candidate
unsigned int ptIndex() const
get pt-code
Definition: L1MuGMTCand.h:78
CombinationsInCond const & getCombinationsInCond() const
get all the object combinations evaluated to true in the condition
bool condLastResult() const
get the latest result for the condition