CMS 3D CMS Logo

Tau.cc
Go to the documentation of this file.
1 //
2 //
3 
6 #include <algorithm>
7 #include <boost/bind.hpp>
8 
9 using namespace pat;
10 
11 
13 Tau::Tau() :
14  Lepton<reco::BaseTau>()
15  ,embeddedIsolationTracks_(false)
16  ,embeddedLeadTrack_(false)
17  ,embeddedSignalTracks_(false)
18  ,embeddedLeadPFCand_(false)
19  ,embeddedLeadPFChargedHadrCand_(false)
20  ,embeddedLeadPFNeutralCand_(false)
21  ,embeddedSignalPFCands_(false)
22  ,embeddedSignalPFChargedHadrCands_(false)
23  ,embeddedSignalPFNeutralHadrCands_(false)
24  ,embeddedSignalPFGammaCands_(false)
25  ,embeddedIsolationPFCands_(false)
26  ,embeddedIsolationPFChargedHadrCands_(false)
27  ,embeddedIsolationPFNeutralHadrCands_(false)
28  ,embeddedIsolationPFGammaCands_(false)
29 {
30 }
31 
33 Tau::Tau(const reco::BaseTau & aTau) :
34  Lepton<reco::BaseTau>(aTau)
35  ,embeddedIsolationTracks_(false)
36  ,embeddedLeadTrack_(false)
37  ,embeddedSignalTracks_(false)
38  ,embeddedLeadPFCand_(false)
39  ,embeddedLeadPFChargedHadrCand_(false)
40  ,embeddedLeadPFNeutralCand_(false)
41  ,embeddedSignalPFCands_(false)
42  ,embeddedSignalPFChargedHadrCands_(false)
43  ,embeddedSignalPFNeutralHadrCands_(false)
44  ,embeddedSignalPFGammaCands_(false)
45  ,embeddedIsolationPFCands_(false)
46  ,embeddedIsolationPFChargedHadrCands_(false)
47  ,embeddedIsolationPFNeutralHadrCands_(false)
48  ,embeddedIsolationPFGammaCands_(false)
49 {
50  const reco::PFTau * pfTau = dynamic_cast<const reco::PFTau *>(&aTau);
51  if (pfTau != nullptr){
52  pfSpecific_.push_back(pat::tau::TauPFSpecific(*pfTau));
53  pfEssential_.push_back(pat::tau::TauPFEssential(*pfTau));
54  }
55  const reco::CaloTau * caloTau = dynamic_cast<const reco::CaloTau *>(&aTau);
56  if (caloTau != nullptr) caloSpecific_.push_back(pat::tau::TauCaloSpecific(*caloTau));
57 }
58 
60 Tau::Tau(const edm::RefToBase<reco::BaseTau> & aTauRef) :
61  Lepton<reco::BaseTau>(aTauRef)
62  ,embeddedIsolationTracks_(false)
63  ,embeddedLeadTrack_(false)
64  ,embeddedSignalTracks_(false)
65  ,embeddedLeadPFCand_(false)
66  ,embeddedLeadPFChargedHadrCand_(false)
67  ,embeddedLeadPFNeutralCand_(false)
68  ,embeddedSignalPFCands_(false)
69  ,embeddedSignalPFChargedHadrCands_(false)
70  ,embeddedSignalPFNeutralHadrCands_(false)
71  ,embeddedSignalPFGammaCands_(false)
72  ,embeddedIsolationPFCands_(false)
73  ,embeddedIsolationPFChargedHadrCands_(false)
74  ,embeddedIsolationPFNeutralHadrCands_(false)
75  ,embeddedIsolationPFGammaCands_(false)
76 {
77  const reco::PFTau * pfTau = dynamic_cast<const reco::PFTau *>(aTauRef.get());
78  if (pfTau != nullptr){
79  pfSpecific_.push_back(pat::tau::TauPFSpecific(*pfTau));
80  pfEssential_.push_back(pat::tau::TauPFEssential(*pfTau));
81  }
82  const reco::CaloTau * caloTau = dynamic_cast<const reco::CaloTau *>(aTauRef.get());
83  if (caloTau != nullptr) caloSpecific_.push_back(pat::tau::TauCaloSpecific(*caloTau));
84 }
85 
87 Tau::Tau(const edm::Ptr<reco::BaseTau> & aTauRef) :
88  Lepton<reco::BaseTau>(aTauRef)
89  ,embeddedIsolationTracks_(false)
90  ,embeddedLeadTrack_(false)
91  ,embeddedSignalTracks_(false)
92  ,embeddedLeadPFCand_(false)
93  ,embeddedLeadPFChargedHadrCand_(false)
94  ,embeddedLeadPFNeutralCand_(false)
95  ,embeddedSignalPFCands_(false)
96  ,embeddedSignalPFChargedHadrCands_(false)
97  ,embeddedSignalPFNeutralHadrCands_(false)
98  ,embeddedSignalPFGammaCands_(false)
99  ,embeddedIsolationPFCands_(false)
100  ,embeddedIsolationPFChargedHadrCands_(false)
101  ,embeddedIsolationPFNeutralHadrCands_(false)
102  ,embeddedIsolationPFGammaCands_(false)
103 {
104  const reco::PFTau * pfTau = dynamic_cast<const reco::PFTau *>(aTauRef.get());
105  if (pfTau != nullptr){
106  pfSpecific_.push_back(pat::tau::TauPFSpecific(*pfTau));
107  pfEssential_.push_back(pat::tau::TauPFEssential(*pfTau));
108  }
109  const reco::CaloTau * caloTau = dynamic_cast<const reco::CaloTau *>(aTauRef.get());
110  if (caloTau != nullptr) caloSpecific_.push_back(pat::tau::TauCaloSpecific(*caloTau));
111 }
112 
114 Tau::~Tau() {
115 }
116 
117 std::ostream&
118 reco::operator<<(std::ostream& out, const pat::Tau& obj)
119 {
120  if(!out) return out;
121 
122  out << "\tpat::Tau: ";
123  out << std::setiosflags(std::ios::right);
124  out << std::setiosflags(std::ios::fixed);
125  out << std::setprecision(3);
126  out << " E/pT/eta/phi "
127  << obj.energy()<<"/"
128  << obj.pt()<<"/"
129  << obj.eta()<<"/"
130  << obj.phi();
131  return out;
132 }
133 
135 const reco::TrackRefVector & Tau::isolationTracks() const {
136  if (embeddedIsolationTracks_) {
137  if (!isolationTracksTransientRefVector_.isSet()) {
138  std::unique_ptr<reco::TrackRefVector> trackRefVec{ new reco::TrackRefVector{}};
139  trackRefVec->reserve(isolationTracks_.size());
140  for (unsigned int i = 0; i < isolationTracks_.size(); i++) {
141  trackRefVec->push_back(reco::TrackRef(&isolationTracks_, i));
142  }
143  isolationTracksTransientRefVector_.set(std::move(trackRefVec));
144  }
145  return *isolationTracksTransientRefVector_;
146  } else {
148  }
149 }
150 
151 
154  if (embeddedLeadTrack_) {
155  return reco::TrackRef(&leadTrack_, 0);
156  } else {
157  return reco::BaseTau::leadTrack();
158  }
159 }
160 
161 
163 const reco::TrackRefVector & Tau::signalTracks() const {
164  if (embeddedSignalTracks_) {
165  if (!signalTracksTransientRefVector_.isSet()) {
166  std::unique_ptr<reco::TrackRefVector> trackRefVec{ new reco::TrackRefVector{} };
167  trackRefVec->reserve(signalTracks_.size());
168  for (unsigned int i = 0; i < signalTracks_.size(); i++) {
169  trackRefVec->push_back(reco::TrackRef(&signalTracks_, i));
170  }
171  signalTracksTransientRefVector_.set(std::move(trackRefVec));
172  }
173  return *signalTracksTransientRefVector_;
174  } else {
176  }
177 }
178 
179 
182  isolationTracks_.clear();
184  for (unsigned int i = 0; i < trackRefVec.size(); i++) {
185  isolationTracks_.push_back(*trackRefVec.at(i));
186  }
187  embeddedIsolationTracks_ = true;
188 }
189 
190 
192 void Tau::embedLeadTrack() {
193  leadTrack_.clear();
194  if (reco::BaseTau::leadTrack().isNonnull()) {
195  leadTrack_.push_back(*reco::BaseTau::leadTrack());
196  embeddedLeadTrack_ = true;
197  }
198 }
199 
200 
203  signalTracks_.clear();
205  for (unsigned int i = 0; i < trackRefVec.size(); i++) {
206  signalTracks_.push_back(*trackRefVec.at(i));
207  }
208  embeddedSignalTracks_ = true;
209 }
210 
211 
213 void Tau::setGenJet(const reco::GenJetRef& gj) {
214  genJet_.clear();
215  genJet_.push_back(*gj);
216 }
217 
219 const reco::GenJet * Tau::genJet() const {
220  return (!genJet_.empty() ? &genJet_.front() : nullptr);
221 }
222 
223 
224 // method to retrieve a tau ID (or throw)
225 float Tau::tauID(const std::string & name) const {
226  for (std::vector<IdPair>::const_iterator it = tauIDs_.begin(), ed = tauIDs_.end(); it != ed; ++it) {
227  if (it->first == name) return it->second;
228  }
229  cms::Exception ex("Key not found");
230  ex << "pat::Tau: the ID " << name << " can't be found in this pat::Tau.\n";
231  ex << "The available IDs are: ";
232  for (std::vector<IdPair>::const_iterator it = tauIDs_.begin(), ed = tauIDs_.end(); it != ed; ++it) {
233  ex << "'" << it->first << "' ";
234  }
235  ex << ".\n";
236  throw ex;
237 }
238 // check if an ID is there
239 bool Tau::isTauIDAvailable(const std::string & name) const {
240  for (std::vector<IdPair>::const_iterator it = tauIDs_.begin(), ed = tauIDs_.end(); it != ed; ++it) {
241  if (it->first == name) return true;
242  }
243  return false;
244 }
245 
246 
247 const pat::tau::TauPFSpecific & Tau::pfSpecific() const {
248  if (!isPFTau()) throw cms::Exception("Type Error") << "Requesting a PFTau-specific information from a pat::Tau which wasn't made from a PFTau.\n";
249  return pfSpecific_[0];
250 }
251 
252 const pat::tau::TauPFEssential & Tau::pfEssential() const {
253  if (pfEssential_.empty()) throw cms::Exception("Type Error") << "Requesting a PFTau-specific information from a pat::Tau which wasn't made from a PFTau.\n";
254  return pfEssential_[0];
255 }
256 
257 
258 const pat::tau::TauCaloSpecific & Tau::caloSpecific() const {
259  if (!isCaloTau()) throw cms::Exception("Type Error") << "Requesting a CaloTau-specific information from a pat::Tau which wasn't made from a CaloTau.\n";
260  return caloSpecific_[0];
261 }
262 
263 reco::Candidate::LorentzVector Tau::p4Jet() const
264 {
265  if ( isCaloTau() ) return caloSpecific().p4Jet_;
266  if ( isPFTau() ) return reco::Candidate::LorentzVector(pfEssential().p4Jet_);
267  throw cms::Exception("Type Error") << "Requesting a CaloTau/PFTau-specific information from a pat::Tau which wasn't made from either a CaloTau or a PFTau.\n";
268 }
269 
270 float Tau::dxy_Sig() const
271 {
272  if ( pfEssential().dxy_error_ != 0 ) return (pfEssential().dxy_/pfEssential().dxy_error_);
273  else return 0.;
274 }
275 
276 pat::tau::TauPFEssential::CovMatrix Tau::flightLengthCov() const
277 {
279  const pat::tau::TauPFEssential::CovMatrix& sv = secondaryVertexCov();
280  const pat::tau::TauPFEssential::CovMatrix& pv = primaryVertexCov();
281  for ( int i = 0; i < dimension; ++i ) {
282  for ( int j = 0; j < dimension; ++j ) {
283  cov(i,j) = sv(i,j) + pv(i,j);
284  }
285  }
286  return cov;
287 }
288 
289 float Tau::ip3d_Sig() const
290 {
291  if( pfEssential().ip3d_error_ != 0 ) return (pfEssential().ip3d_/pfEssential().ip3d_error_);
292  else return 0.;
293 }
294 
295 float Tau::etaetaMoment() const
296 {
297  if ( isCaloTau() ) return caloSpecific().etaetaMoment_;
298  if ( isPFTau() ) return pfSpecific().etaetaMoment_;
299  throw cms::Exception("Type Error") << "Requesting a CaloTau/PFTau-specific information from a pat::Tau which wasn't made from either a CaloTau or a PFTau.\n";
300 }
301 
302 float Tau::phiphiMoment() const
303 {
304  if ( isCaloTau() ) return caloSpecific().phiphiMoment_;
305  if ( isPFTau() ) return pfSpecific().phiphiMoment_;
306  throw cms::Exception("Type Error") << "Requesting a CaloTau/PFTau-specific information from a pat::Tau which wasn't made from either a CaloTau or a PFTau.\n";
307 }
308 
309 float Tau::etaphiMoment() const
310 {
311  if ( isCaloTau() ) return caloSpecific().etaphiMoment_;
312  if ( isPFTau() ) return pfSpecific().etaphiMoment_;
313  throw cms::Exception("Type Error") << "Requesting a CaloTau/PFTau-specific information from a pat::Tau which wasn't made from either a CaloTau or a PFTau.\n";
314 }
315 
316 void Tau::setDecayMode(int decayMode)
317 {
318  if (!isPFTau()) throw cms::Exception("Type Error") << "Requesting a PFTau-specific information from a pat::Tau which wasn't made from a PFTau.\n";
319  pfEssential_[0].decayMode_ = decayMode;
320 }
321 
323 void Tau::embedLeadPFCand() {
324  if (!isPFTau() ) {//additional check with warning in pat::tau producer
325  return;
326  }
327  leadPFCand_.clear();
328  if (pfSpecific_[0].leadPFCand_.isNonnull() ) {
329  leadPFCand_.push_back(*pfSpecific_[0].leadPFCand_); //already set in C-tor
330  embeddedLeadPFCand_ = true;
331  }
332 }
335  if (!isPFTau() ) {//additional check with warning in pat::tau producer
336  return;
337  }
338  leadPFChargedHadrCand_.clear();
339  if (pfSpecific_[0].leadPFChargedHadrCand_.isNonnull() ) {
340  leadPFChargedHadrCand_.push_back(*pfSpecific_[0].leadPFChargedHadrCand_); //already set in C-tor
341  embeddedLeadPFChargedHadrCand_ = true;
342  }
343 }
346  if (!isPFTau() ) {//additional check with warning in pat::tau producer
347  return;
348  }
349  leadPFNeutralCand_.clear();
350  if (pfSpecific_[0].leadPFNeutralCand_.isNonnull() ) {
351  leadPFNeutralCand_.push_back(*pfSpecific_[0].leadPFNeutralCand_); //already set in C-tor
352  embeddedLeadPFNeutralCand_ = true;
353  }
354 }
355 
357  if (!isPFTau() ) {//additional check with warning in pat::tau producer
358  return;
359  }
360  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedSignalPFCands_;
361  for (unsigned int i = 0; i < candPtrs.size(); i++) {
362  signalPFCands_.push_back(*candPtrs.at(i));
363  }
364  embeddedSignalPFCands_ = true;
365 }
367  if (!isPFTau() ) {//additional check with warning in pat::tau producer
368  return;
369  }
370  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedSignalPFChargedHadrCands_;
371  for (unsigned int i = 0; i < candPtrs.size(); i++) {
372  signalPFChargedHadrCands_.push_back(*candPtrs.at(i));
373  }
374  embeddedSignalPFChargedHadrCands_ = true;
375 }
377  if (!isPFTau() ) {//additional check with warning in pat::tau producer
378  return;
379  }
380  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedSignalPFNeutrHadrCands_;
381  for (unsigned int i = 0; i < candPtrs.size(); i++) {
382  signalPFNeutralHadrCands_.push_back(*candPtrs.at(i));
383  }
384  embeddedSignalPFNeutralHadrCands_ = true;
385 }
387  if (!isPFTau() ) {//additional check with warning in pat::tau producer
388  return;
389  }
390  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedSignalPFGammaCands_;
391  for (unsigned int i = 0; i < candPtrs.size(); i++) {
392  signalPFGammaCands_.push_back(*candPtrs.at(i));
393  }
394  embeddedSignalPFGammaCands_ = true;
395 }
396 
398  if (!isPFTau() ) {//additional check with warning in pat::tau producer
399  return;
400  }
401  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedIsolationPFCands_;
402  for (unsigned int i = 0; i < candPtrs.size(); i++) {
403  isolationPFCands_.push_back(*candPtrs.at(i));
404  }
405  embeddedIsolationPFCands_ = true;
406 }
407 
409  if (!isPFTau() ) {//additional check with warning in pat::tau producer
410  return;
411  }
412  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedIsolationPFChargedHadrCands_;
413  for (unsigned int i = 0; i < candPtrs.size(); i++) {
414  isolationPFChargedHadrCands_.push_back(*candPtrs.at(i));
415  }
416  embeddedIsolationPFChargedHadrCands_ = true;
417 }
419  if (!isPFTau() ) {//additional check with warning in pat::tau producer
420  return;
421  }
422  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedIsolationPFNeutrHadrCands_;
423  for (unsigned int i = 0; i < candPtrs.size(); i++) {
424  isolationPFNeutralHadrCands_.push_back(*candPtrs.at(i));
425  }
426  embeddedIsolationPFNeutralHadrCands_ = true;
427 }
429  if (!isPFTau() ) {//additional check with warning in pat::tau producer
430  return;
431  }
432  std::vector<reco::PFCandidatePtr> candPtrs = pfSpecific_[0].selectedIsolationPFGammaCands_;
433  for (unsigned int i = 0; i < candPtrs.size(); i++) {
434  isolationPFGammaCands_.push_back(*candPtrs.at(i));
435  }
436  embeddedIsolationPFGammaCands_ = true;
437 }
438 
439 reco::PFRecoTauChargedHadronRef Tau::leadTauChargedHadronCandidate() const {
440  if(!isPFTau() ) throw cms::Exception("Type Error") << "Requesting content that is not stored in miniAOD.\n";
441  if ( !pfSpecific().signalTauChargedHadronCandidates_.empty() ) {
442  return reco::PFRecoTauChargedHadronRef(&pfSpecific().signalTauChargedHadronCandidates_,0);
443  } else {
445  }
446 }
447 
448 const reco::PFCandidatePtr Tau::leadPFChargedHadrCand() const {
449  if(!embeddedLeadPFChargedHadrCand_){
450  if(pfSpecific_.empty()) return reco::PFCandidatePtr();
451  else return pfSpecific().leadPFChargedHadrCand_;
452  }else
453  return reco::PFCandidatePtr(&leadPFChargedHadrCand_,0);
454 }
455 
456 const reco::PFCandidatePtr Tau::leadPFNeutralCand() const {
457  if(!embeddedLeadPFNeutralCand_){
458  if(pfSpecific_.empty()) return reco::PFCandidatePtr();
459  else return pfSpecific().leadPFNeutralCand_;
460  }else
461  return reco::PFCandidatePtr(&leadPFNeutralCand_,0);
462 }
463 
464 const reco::PFCandidatePtr Tau::leadPFCand() const {
465  if(!embeddedLeadPFCand_){
466  if(pfSpecific_.empty()) return reco::PFCandidatePtr();
467  return pfSpecific().leadPFCand_;
468  }else
469  return reco::PFCandidatePtr(&leadPFCand_,0);
470 }
471 
472 const std::vector<reco::PFCandidatePtr>& Tau::signalPFCands() const {
473  if (embeddedSignalPFCands_) {
474  if (!signalPFCandsTransientPtrs_.isSet()) {
475  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
476  aPtrs->reserve(signalPFCands_.size());
477  for (unsigned int i = 0; i < signalPFCands_.size(); i++) {
478  aPtrs->push_back(reco::PFCandidatePtr(&signalPFCands_, i) );
479  }
480  signalPFCandsTransientPtrs_.set(std::move(aPtrs));
481  }
482  return *signalPFCandsTransientPtrs_;
483  } else {
484  if(pfSpecific_.empty() || pfSpecific().selectedSignalPFCands_.empty() || !pfSpecific().selectedSignalPFCands_.front().isAvailable()){
485  // this part of code is called when reading from patTuple or miniAOD
486  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
487  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
488  signalPFCandsTransientPtrs_.set(std::move(aPtrs));
489  return *signalPFCandsTransientPtrs_;
490  } else return pfSpecific().selectedSignalPFCands_;
491  }
492 }
493 
494 const std::vector<reco::PFCandidatePtr>& Tau::signalPFChargedHadrCands() const {
495  if (embeddedSignalPFChargedHadrCands_) {
496  if (!signalPFChargedHadrCandsTransientPtrs_.isSet()) {
497  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{ new std::vector<reco::PFCandidatePtr>{}};
498  aPtrs->reserve(signalPFChargedHadrCands_.size());
499  for (unsigned int i = 0; i < signalPFChargedHadrCands_.size(); i++) {
500  aPtrs->push_back(reco::PFCandidatePtr(&signalPFChargedHadrCands_, i) );
501  }
502  signalPFChargedHadrCandsTransientPtrs_.set(std::move(aPtrs));
503  }
504  return *signalPFChargedHadrCandsTransientPtrs_;
505  } else {
506  if(pfSpecific_.empty() || pfSpecific().selectedSignalPFChargedHadrCands_.empty() || !pfSpecific().selectedSignalPFChargedHadrCands_.front().isAvailable()){
507  // this part of code is called when reading from patTuple or miniAOD
508  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
509  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
510  signalPFChargedHadrCandsTransientPtrs_.set(std::move(aPtrs));
511  return *signalPFChargedHadrCandsTransientPtrs_;
512  } else return pfSpecific().selectedSignalPFChargedHadrCands_;
513  }
514 }
515 
516 const std::vector<reco::PFCandidatePtr>& Tau::signalPFNeutrHadrCands() const {
517  if (embeddedSignalPFNeutralHadrCands_) {
518  if (!signalPFNeutralHadrCandsTransientPtrs_.isSet()) {
519  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
520  aPtrs->reserve(signalPFNeutralHadrCands_.size());
521  for (unsigned int i = 0; i < signalPFNeutralHadrCands_.size(); i++) {
522  aPtrs->push_back(reco::PFCandidatePtr(&signalPFNeutralHadrCands_, i) );
523  }
524  signalPFNeutralHadrCandsTransientPtrs_.set(std::move(aPtrs));
525  }
526  return *signalPFNeutralHadrCandsTransientPtrs_;
527  } else {
528  if(pfSpecific_.empty() || pfSpecific().selectedSignalPFNeutrHadrCands_.empty() || !pfSpecific().selectedSignalPFNeutrHadrCands_.front().isAvailable()){
529  // this part of code is called when reading from patTuple or miniAOD
530  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
531  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
532  signalPFNeutralHadrCandsTransientPtrs_.set(std::move(aPtrs));
533  return *signalPFNeutralHadrCandsTransientPtrs_;
534  } else return pfSpecific().selectedSignalPFNeutrHadrCands_;
535  }
536 }
537 
538 const std::vector<reco::PFCandidatePtr>& Tau::signalPFGammaCands() const {
539  if (embeddedSignalPFGammaCands_) {
540  if (!signalPFGammaCandsTransientPtrs_.isSet()) {
541  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{ new std::vector<reco::PFCandidatePtr>{}};
542  aPtrs->reserve(signalPFGammaCands_.size());
543  for (unsigned int i = 0; i < signalPFGammaCands_.size(); i++) {
544  aPtrs->push_back(reco::PFCandidatePtr(&signalPFGammaCands_, i) );
545  }
546  signalPFGammaCandsTransientPtrs_.set(std::move(aPtrs));
547  }
548  return *signalPFGammaCandsTransientPtrs_;
549  } else {
550  if(pfSpecific_.empty() || pfSpecific().selectedSignalPFGammaCands_.empty() || !pfSpecific().selectedSignalPFGammaCands_.front().isAvailable()){
551  // this part of code is called when reading from patTuple or miniAOD
552  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
553  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
554  signalPFGammaCandsTransientPtrs_.set(std::move(aPtrs));
555  return *signalPFGammaCandsTransientPtrs_;
556  } else return pfSpecific().selectedSignalPFGammaCands_;
557  }
558 }
559 
560 const std::vector<reco::PFRecoTauChargedHadron> & Tau::signalTauChargedHadronCandidates() const {
561  if(pfSpecific_.empty()) throw cms::Exception("Type Error") << "Requesting content that is not stored in miniAOD.\n";
562  return pfSpecific().signalTauChargedHadronCandidates_;
563 }
564 
565 const std::vector<reco::RecoTauPiZero> & Tau::signalPiZeroCandidates() const {
566  if(pfSpecific_.empty()) throw cms::Exception("Type Error") << "Requesting content that is not stored in miniAOD.\n";
567  return pfSpecific().signalPiZeroCandidates_;
568 }
569 
570 const std::vector<reco::PFCandidatePtr>& Tau::isolationPFCands() const {
571  if (embeddedIsolationPFCands_) {
572  if (!isolationPFCandsTransientPtrs_.isSet()) {
573  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{ new std::vector<reco::PFCandidatePtr>{}};
574  aPtrs->reserve(isolationPFCands_.size());
575  for (unsigned int i = 0; i < isolationPFCands_.size(); i++) {
576  aPtrs->push_back(reco::PFCandidatePtr(&isolationPFCands_, i) );
577  }
578  isolationPFCandsTransientPtrs_.set(std::move(aPtrs));
579  }
580  return *isolationPFCandsTransientPtrs_;
581  } else {
582  if(pfSpecific_.empty() || pfSpecific().selectedIsolationPFCands_.empty() || !pfSpecific().selectedIsolationPFCands_.front().isAvailable()){
583  // this part of code is called when reading from patTuple or miniAOD
584  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
585  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
586  isolationPFCandsTransientPtrs_.set(std::move(aPtrs));
587  return *isolationPFCandsTransientPtrs_;
588  } else return pfSpecific().selectedIsolationPFCands_;
589  }
590 }
591 
592 const std::vector<reco::PFCandidatePtr>& Tau::isolationPFChargedHadrCands() const {
593  if (embeddedIsolationPFChargedHadrCands_) {
594  if (!isolationPFChargedHadrCandsTransientPtrs_.isSet()) {
595  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{ new std::vector<reco::PFCandidatePtr>{}};
596  aPtrs->reserve(isolationPFChargedHadrCands_.size());
597  for (unsigned int i = 0; i < isolationPFChargedHadrCands_.size(); i++) {
598  aPtrs->push_back(reco::PFCandidatePtr(&isolationPFChargedHadrCands_, i) );
599  }
600  isolationPFChargedHadrCandsTransientPtrs_.set(std::move(aPtrs));
601  }
602  return *isolationPFChargedHadrCandsTransientPtrs_;
603  } else {
604  if(pfSpecific_.empty() || pfSpecific().selectedIsolationPFChargedHadrCands_.empty() || !pfSpecific().selectedIsolationPFChargedHadrCands_.front().isAvailable()){
605  // this part of code is called when reading from patTuple or miniAOD
606  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
607  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
608  isolationPFChargedHadrCandsTransientPtrs_.set(std::move(aPtrs));
609  return *isolationPFChargedHadrCandsTransientPtrs_;
610  } else return pfSpecific().selectedIsolationPFChargedHadrCands_;
611  }
612 }
613 
614 const std::vector<reco::PFCandidatePtr>& Tau::isolationPFNeutrHadrCands() const {
615  if (embeddedIsolationPFNeutralHadrCands_) {
616  if (!isolationPFNeutralHadrCandsTransientPtrs_.isSet()) {
617  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{ new std::vector<reco::PFCandidatePtr>{}};
618  aPtrs->reserve(isolationPFNeutralHadrCands_.size());
619  for (unsigned int i = 0; i < isolationPFNeutralHadrCands_.size(); i++) {
620  aPtrs->push_back(reco::PFCandidatePtr(&isolationPFNeutralHadrCands_, i) );
621  }
622  isolationPFNeutralHadrCandsTransientPtrs_.set(std::move(aPtrs));
623  }
624  return *isolationPFNeutralHadrCandsTransientPtrs_;
625  } else {
626  if(pfSpecific_.empty() || pfSpecific().selectedIsolationPFNeutrHadrCands_.empty() || !pfSpecific().selectedIsolationPFNeutrHadrCands_.front().isAvailable()){
627  // this part of code is called when reading from patTuple or miniAOD
628  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
629  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
630  isolationPFNeutralHadrCandsTransientPtrs_.set(std::move(aPtrs));
631  return *isolationPFNeutralHadrCandsTransientPtrs_;
632  } else return pfSpecific().selectedIsolationPFNeutrHadrCands_;
633  }
634 }
635 
636 const std::vector<reco::PFCandidatePtr>& Tau::isolationPFGammaCands() const {
637  if (embeddedIsolationPFGammaCands_) {
638  if (!isolationPFGammaCandsTransientPtrs_.isSet()) {
639  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
640  aPtrs->reserve(isolationPFGammaCands_.size());
641  for (unsigned int i = 0; i < isolationPFGammaCands_.size(); i++) {
642  aPtrs->push_back(reco::PFCandidatePtr(&isolationPFGammaCands_, i) );
643  }
644  isolationPFGammaCandsTransientPtrs_.set(std::move(aPtrs));
645  }
646  return *isolationPFGammaCandsTransientPtrs_;
647  } else {
648  if(pfSpecific_.empty() || pfSpecific().selectedIsolationPFGammaCands_.empty() || !pfSpecific().selectedIsolationPFGammaCands_.front().isAvailable()){
649  // this part of code is called when reading from patTuple or miniAOD
650  // it returns empty collection in correct format so it can be substituted by reco::Candidates if available
651  std::unique_ptr<std::vector<reco::PFCandidatePtr> > aPtrs{new std::vector<reco::PFCandidatePtr>{}};
652  isolationPFGammaCandsTransientPtrs_.set(std::move(aPtrs));
653  return *isolationPFGammaCandsTransientPtrs_;
654  } else return pfSpecific().selectedIsolationPFGammaCands_;
655  }
656 }
657 
658 const std::vector<reco::PFRecoTauChargedHadron> & Tau::isolationTauChargedHadronCandidates() const {
659  if(pfSpecific_.empty()) throw cms::Exception("Type Error") << "Requesting content that is not stored in miniAOD.\n";
660  return pfSpecific().isolationTauChargedHadronCandidates_;
661 }
662 
663 const std::vector<reco::RecoTauPiZero> & Tau::isolationPiZeroCandidates() const {
664  if(pfSpecific_.empty()) throw cms::Exception("Type Error") << "Requesting content that is not stored in miniAOD.\n";
665  return pfSpecific().isolationPiZeroCandidates_;
666 }
667 
670 
671 // initialize the jet to a given JEC level during creation starting from Uncorrected
672 void Tau::initializeJEC(unsigned int level, unsigned int set)
673 {
674  currentJECSet(set);
675  currentJECLevel(level);
676  setP4(jec_[set].correction(level)*p4());
677 }
678 
680 int Tau::jecSet(const std::string& set) const
681 {
682  for ( std::vector<pat::TauJetCorrFactors>::const_iterator corrFactor = jec_.begin();
683  corrFactor != jec_.end(); ++corrFactor ) {
684  if ( corrFactor->jecSet() == set ) return corrFactor-jec_.begin();
685  }
686  return -1;
687 }
688 
690 const std::vector<std::string> Tau::availableJECSets() const
691 {
692  std::vector<std::string> sets;
693  for ( std::vector<pat::TauJetCorrFactors>::const_iterator corrFactor = jec_.begin();
694  corrFactor != jec_.end(); ++corrFactor ) {
695  sets.push_back(corrFactor->jecSet());
696  }
697  return sets;
698 }
699 
700 const std::vector<std::string> Tau::availableJECLevels(const int& set) const
701 {
702  return set>=0 ? jec_.at(set).correctionLabels() : std::vector<std::string>();
703 }
704 
707 float Tau::jecFactor(const std::string& level, const std::string& set) const
708 {
709  for ( unsigned int idx = 0; idx < jec_.size(); ++idx ) {
710  if ( set.empty() || jec_.at(idx).jecSet() == set ){
711  if ( jec_[idx].jecLevel(level) >= 0 )
712  return jecFactor(jec_[idx].jecLevel(level), idx);
713  else
714  throw cms::Exception("InvalidRequest")
715  << "This JEC level " << level << " does not exist. \n";
716  }
717  }
718  throw cms::Exception("InvalidRequest")
719  << "This jet does not carry any jet energy correction factor information \n"
720  << "for a jet energy correction set with label " << set << "\n";
721 }
722 
725 float Tau::jecFactor(const unsigned int& level, const unsigned int& set) const
726 {
727  if ( !jecSetsAvailable() )
728  throw cms::Exception("InvalidRequest")
729  << "This jet does not carry any jet energy correction factor information \n";
730  if ( !jecSetAvailable(set) )
731  throw cms::Exception("InvalidRequest")
732  << "This jet does not carry any jet energy correction factor information \n"
733  << "for a jet energy correction set with index " << set << "\n";
734  return jec_.at(set).correction(level)/jec_.at(currentJECSet_).correction(currentJECLevel_);
735 }
736 
739 Tau Tau::correctedTauJet(const std::string& level, const std::string& set) const
740 {
741  // rescale p4 of the jet; the update of current values is
742  // done within the called jecFactor function
743  for ( unsigned int idx = 0; idx < jec_.size(); ++idx ) {
744  if ( set.empty() || jec_.at(idx).jecSet() == set ) {
745  if ( jec_[idx].jecLevel(level) >= 0 )
746  return correctedTauJet(jec_[idx].jecLevel(level), idx);
747  else
748  throw cms::Exception("InvalidRequest")
749  << "This JEC level " << level << " does not exist. \n";
750  }
751  }
752  throw cms::Exception("InvalidRequest")
753  << "This JEC set " << set << " does not exist. \n";
754 }
755 
758 Tau Tau::correctedTauJet(const unsigned int& level, const unsigned int& set) const
759 {
760  Tau correctedTauJet(*this);
761  //rescale p4 of the jet
762  correctedTauJet.setP4(jecFactor(level, set)*p4());
763  // update current level and set
764  correctedTauJet.currentJECSet(set);
765  correctedTauJet.currentJECLevel(level);
766  return correctedTauJet;
767 }
768 
769 
770 
773 // return the leading candidate from signal(PF)ChargedHadrCandPtrs_ collection
774 const reco::CandidatePtr Tau::leadChargedHadrCand() const {
775  const reco::PFCandidatePtr leadPF = leadPFChargedHadrCand();
776  if (leadPF.isAvailable() || signalChargedHadrCandPtrs_.isNull()) return leadPF;
777  reco::CandidatePtr ret;
778  for (const reco::CandidatePtr & p : signalChargedHadrCandPtrs_) {
779  if (ret.isNull() || (p->pt() > ret->pt())) ret = p;
780  }
781  return ret;
782 
783 }
784 
786 const reco::CandidatePtr Tau::leadNeutralCand() const {
787  const reco::PFCandidatePtr leadPF = leadPFNeutralCand();
788  if (leadPF.isAvailable() || signalNeutralHadrCandPtrs_.isNull()) return leadPF;
789  reco::CandidatePtr ret;
790  for (const reco::CandidatePtr & p : signalNeutralHadrCandPtrs_) {
791  if (ret.isNull() || (p->pt() > ret->pt())) ret = p;
792  }
793  return ret;
794 
795 }
796 
798 const reco::CandidatePtr Tau::leadCand() const {
799  const reco::PFCandidatePtr leadPF = leadPFCand();
800  if (leadPF.isAvailable() || !Tau::ExistSignalCands()) return leadPF;
801  else return Tau::signalCands()[0];
802 }
803 
805 
806 bool Tau::ExistSignalCands() const {
807  return !(signalChargedHadrCandPtrs_.isNull() && signalNeutralHadrCandPtrs_.isNull() && signalGammaCandPtrs_.isNull());
808 }
809 
810 bool Tau::ExistIsolationCands() const {
811  return !(isolationChargedHadrCandPtrs_.isNull() && isolationNeutralHadrCandPtrs_.isNull() && isolationGammaCandPtrs_.isNull());
812 }
813 
816 
817 reco::CandidatePtrVector Tau::signalCands() const {
818  std::vector<reco::PFCandidatePtr> r0 = signalPFCands();
820  if(!Tau::ExistSignalCands() || (!r0.empty() && r0.front().isAvailable())) {
821  for (const auto & p : r0) ret.push_back(p);
822  return ret;
823  } else {
826  std::vector<std::pair<float,size_t> > pt_index;
827  size_t index=0;
828  for (const auto & p : signalChargedHadrCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
829  for (const auto & p : signalNeutralHadrCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
830  for (const auto & p : signalGammaCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
831  std::sort(pt_index.begin(),pt_index.end(),
832  boost::bind(&std::pair<float,size_t>::first,_1) >
833  boost::bind(&std::pair<float,size_t>::first,_2));
834  for( const auto & p : pt_index){
835  ret.push_back(ret2[p.second]);
836  }
837  return ret;
838  }
839 }
840 
843 reco::CandidatePtrVector Tau::signalChargedHadrCands() const {
844  std::vector<reco::PFCandidatePtr> r0 = signalPFChargedHadrCands();
845  if(signalChargedHadrCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
847  for (const auto & p : r0) ret.push_back(p);
848  return ret;
849  } else {
850  return signalChargedHadrCandPtrs_;
851  }
852 }
853 
854 
857 reco::CandidatePtrVector Tau::signalNeutrHadrCands() const {
858  std::vector<reco::PFCandidatePtr> r0 = signalPFNeutrHadrCands();
859  if(signalNeutralHadrCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
861  for (const auto & p : r0) ret.push_back(p);
862  return ret;
863  } else {
864  return signalNeutralHadrCandPtrs_;
865  }
866 }
867 
870 reco::CandidatePtrVector Tau::signalGammaCands() const {
871  std::vector<reco::PFCandidatePtr> r0 = signalPFGammaCands();
872  if(signalGammaCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
874  for (const auto & p : r0) ret.push_back(p);
875  return ret;
876  } else {
877  return signalGammaCandPtrs_;
878  }
879 }
880 
883 reco::CandidatePtrVector Tau::isolationCands() const {
884  std::vector<reco::PFCandidatePtr> r0 = isolationPFCands();
886  if(!Tau::ExistIsolationCands() || (!r0.empty() && r0.front().isAvailable())) {
887  for (const auto & p : r0) ret.push_back(p);
888  return ret;
889  } else {
892  std::vector<std::pair<float,size_t> > pt_index;
893  size_t index=0;
894  for (const auto & p : isolationChargedHadrCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
895  for (const auto & p : isolationNeutralHadrCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
896  for (const auto & p : isolationGammaCandPtrs_){ ret2.push_back(p); pt_index.push_back(std::make_pair(p->pt(),index)); index++;}
897  std::sort(pt_index.begin(),pt_index.end(),
898  boost::bind(&std::pair<float,size_t>::first,_1) >
899  boost::bind(&std::pair<float,size_t>::first,_2));
900  for( const auto & p : pt_index){
901  ret.push_back(ret2[p.second]);
902  }
903  return ret;
904  }
905 }
906 
909 reco::CandidatePtrVector Tau::isolationChargedHadrCands() const {
910  std::vector<reco::PFCandidatePtr> r0 = isolationPFChargedHadrCands();
911  if(isolationChargedHadrCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
913  for (const auto & p : r0) ret.push_back(p);
914  return ret;
915  } else {
916  return isolationChargedHadrCandPtrs_;
917  }
918 }
919 
922 reco::CandidatePtrVector Tau::isolationNeutrHadrCands() const {
924  std::vector<reco::PFCandidatePtr> r0 = isolationPFNeutrHadrCands();
925  if(isolationNeutralHadrCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
927  for (const auto & p : r0) ret.push_back(p);
928  return ret;
929  } else {
930  return isolationNeutralHadrCandPtrs_;
931  }
932 }
933 
936 reco::CandidatePtrVector Tau::isolationGammaCands() const {
937  std::vector<reco::PFCandidatePtr> r0 = isolationPFGammaCands();
938  if(isolationGammaCandPtrs_.isNull() || (!r0.empty() && r0.front().isAvailable())) {
940  for (const auto & p : r0) ret.push_back(p);
941  return ret;
942  } else {
943  return isolationGammaCandPtrs_;
944  }
945 }
946 
947 
948 
951 size_t Tau::numberOfSourceCandidatePtrs() const {
952  if (Tau::ExistSignalCands()) return Tau::signalCands().size();
953  else if(pfSpecific_.empty()) return 0;
954  else return pfSpecific().selectedSignalPFCands_.size();
955 }
957 reco::CandidatePtr Tau::sourceCandidatePtr( size_type i ) const {
958  if (Tau::ExistSignalCands()) return Tau::signalCands()[i];
959  else if(pfSpecific_.empty()) return reco::CandidatePtr();
960  else return pfSpecific().selectedSignalPFCands_[i];
961 }
962 
963 
964 
965 
value_type const * get() const
Definition: RefToBase.h:234
virtual reco::TrackRef leadTrack() const
Definition: BaseTau.cc:26
embedIsolationPFNeutralHadrCands
embed in AOD externally stored isolation PFChargedHadronCandidates
size_type size() const
Size of the RefVector.
Definition: PtrVectorBase.h:74
double eta() const final
momentum pseudorapidity
embedIsolationPFChargedHadrCands
embed in AOD externally stored isolation PFCandidates
virtual const reco::TrackRefVector & isolationTracks() const
Definition: BaseTau.cc:30
void push_back(Ptr< T > const &iPtr)
Definition: PtrVector.h:140
T const * get() const
Returns C++ pointer to the item.
Definition: Ptr.h:159
bool isAvailable() const
Definition: Ptr.h:258
embedSignalPFGammaCands
embed in AOD externally stored signal PFNeutralHadronCandidates
embedSignalPFCands
embed in AOD externally stored leading PFNeutral Candidate
double pt() const final
transverse momentum
uint16_t size_type
embedSignalPFNeutralHadrCands
embed in AOD externally stored signal PFChargedHadronCandidates
Definition: HeavyIon.h:7
static const int tauID
Definition: TopGenEvent.h:21
embedSignalTracks
embed in AOD externally stored leading track
std::ostream & operator<<(std::ostream &, BeamSpot beam)
Definition: BeamSpot.cc:71
embedIsolationPFGammaCands
embed in AOD externally stored isolation PFNeutralHadronCandidates
embedIsolationTracks
embed in AOD externally stored signal tracks
Tau()
default constructor
double p4[4]
Definition: TauolaWrapper.h:92
double energy() const final
energy
bool isNull() const
Checks for null.
Definition: Ptr.h:164
def pv(vc)
Definition: MetAnalyzer.py:6
Jets made from MC generator particles.
Definition: GenJet.h:24
embedLeadPFNeutralCand
embed in AOD externally stored leading PFChargedHadron candidate
virtual const reco::TrackRefVector & signalTracks() const
Definition: BaseTau.cc:28
void reserve(size_type n)
Reserve space for RefVector.
Definition: RefVector.h:113
std::string currentJECLevel() const
return the name of the current step of jet energy corrections
Definition: Tau.h:410
Analysis-level tau class.
Definition: Tau.h:55
InputIterator leadPFCand(InputIterator begin, InputIterator end)
Definition: Tau.py:1
embedSignalPFChargedHadrCands
embed in AOD externally stored signal PFCandidates
virtual double pt() const =0
transverse momentum
edm::Ref< TrackCollection > TrackRef
persistent reference to a Track
Definition: TrackFwd.h:21
edm::Ref< PFRecoTauChargedHadronCollection > PFRecoTauChargedHadronRef
presistent reference to a PFRecoTauChargedHadron
math::XYZTLorentzVector LorentzVector
Lorentz vector.
Definition: Candidate.h:37
fixed size matrix
value_type const at(size_type idx) const
Retrieve an element of the RefVector.
Definition: RefVector.h:88
embedIsolationPFCands
embed in AOD externally stored signal PFGammaCandidates
size_type size() const
Size of the RefVector.
Definition: RefVector.h:107
Definition: Lepton.py:1
embedLeadPFCand
embed in AOD externally stored isolation tracks embedding objects (for PFTaus only) ...
embedLeadPFChargedHadrCand
embed in AOD externally stored leading PFCandidate
std::string currentJECSet() const
returns the label of the current set of jet energy corrections
Definition: Tau.h:406
uint32_t dimension(pat::CandKinResolution::Parametrization parametrization)
Returns the number of free parameters in a parametrization (3 or 4)
edm::Ptr< PFCandidate > PFCandidatePtr
persistent Ptr to a PFCandidate
double phi() const final
momentum azimuthal angle
void setP4(const LorentzVector &p4) final
set 4-momentum
def move(src, dest)
Definition: eostools.py:510
math::ErrorF< 3 >::type CovMatrix