00001 #include "RecoTauTag/TauTagTools/interface/GeneratorTau.h" 00002 00003 float GeneratorTau::getVisNuAngle() const { 00004 LorentzVector suckVector = getVisibleFourVector(); 00005 LorentzVector suckNuVector = this->p4() - suckVector; 00006 return angleFinder(suckVector, suckNuVector); 00007 } 00008 00009 const reco::Candidate* GeneratorTau::getLeadTrack() const { 00010 return static_cast<const Candidate*>(theLeadTrack_); 00011 } 00012 00013 const reco::GenParticle* GeneratorTau::findLeadTrack() { 00014 std::vector<const reco::GenParticle*>::const_iterator thePion = 00015 genChargedPions_.begin(); 00016 double maxPt = 0; 00017 const reco::GenParticle* output = NULL; 00018 for (; thePion != genChargedPions_.end(); ++thePion) { 00019 if ((*thePion)->pt() > maxPt) { 00020 maxPt = (*thePion)->pt(); 00021 output = (*thePion); 00022 } 00023 } 00024 theLeadTrack_ = output; 00025 return output; 00026 } 00027 00028 float GeneratorTau::getOpeningAngle( 00029 const std::vector<const reco::GenParticle*>& theCollection) const { 00030 double output = 0; 00031 std::vector<const reco::GenParticle*>::const_iterator theObject = 00032 theCollection.begin(); 00033 for (; theObject != theCollection.end(); ++theObject) { 00034 if (output < angleFinder(theLeadTrack_->p4(), (*theObject)->p4())) 00035 output = angleFinder(theLeadTrack_->p4(), (*theObject)->p4()); 00036 } 00037 return output; 00038 } 00039 00040 float GeneratorTau::getChargedOpeningAngle() const { 00041 return getOpeningAngle(genChargedPions_); 00042 } 00043 00044 float GeneratorTau::getGammaOpeningAngle() const { 00045 return getOpeningAngle(genGammas_); 00046 } 00047 00048 GeneratorTau::tauDecayModeEnum GeneratorTau::computeDecayMode( 00049 const reco::GenParticle* theTau) { 00050 //return kUndefined if not a tau 00051 if (theTau == NULL || std::abs(theTau->pdgId()) != 15 00052 || theTau->status() != 2) 00053 return kUndefined; 00054 00055 tauDecayModeEnum output; 00056 00057 //counters to determine decay type (adapted from Ricardo's code) 00058 int numElectrons = 0; 00059 int numMuons = 0; 00060 int numChargedPions = 0; 00061 int numNeutralPions = 0; 00062 int numNeutrinos = 0; 00063 int numOtherParticles = 0; 00064 00066 std::vector<const reco::GenParticle* > pdgDecayProductTypes; 00067 00068 GeneratorTau::decayToPDGClassification(theTau, pdgDecayProductTypes); 00069 00070 for (std::vector<const reco::GenParticle* >::const_iterator decayProduct = 00071 pdgDecayProductTypes.begin(); 00072 decayProduct != pdgDecayProductTypes.end(); ++decayProduct) { 00073 int pdg_id = std::abs( (*decayProduct)->pdgId() ); 00074 //edm::LogInfo("GeneratorTau") << "Has decay product w/ PDG ID: " << pdg_id; 00075 if (pdg_id == 11) numElectrons++; 00076 else if (pdg_id == 13) numMuons++; 00077 else if (pdg_id == 211) numChargedPions++; 00078 else if (pdg_id == 111) numNeutralPions++; 00079 else if (pdg_id == 12 || 00080 pdg_id == 14 || 00081 pdg_id == 16) numNeutrinos++; 00082 else if (pdg_id != 22) 00083 numOtherParticles++; 00084 } 00085 output = kOther; 00086 00087 //determine tauDecayMode 00088 if ( numOtherParticles == 0 ){ 00089 if ( numElectrons == 1 ){ 00090 //--- tau decays into electrons 00091 output = kElectron; 00092 } else if ( numMuons == 1 ){ 00093 //--- tau decays into muons 00094 output = kMuon; 00095 } else { 00096 //--- hadronic tau decays 00097 switch ( numChargedPions ){ 00098 case 1 : 00099 switch ( numNeutralPions ){ 00100 case 0 : 00101 output = kOneProng0pi0; 00102 break; 00103 case 1 : 00104 output = kOneProng1pi0; 00105 break; 00106 case 2 : 00107 output = kOneProng2pi0; 00108 break; 00109 } 00110 break; 00111 case 3 : 00112 switch ( numNeutralPions ){ 00113 case 0 : 00114 output = kThreeProng0pi0; 00115 break; 00116 case 1 : 00117 output = kThreeProng1pi0; 00118 break; 00119 } 00120 break; 00121 } 00122 } 00123 } 00124 return output; 00125 } 00126 00128 void 00129 GeneratorTau::decayToPDGClassification(const reco::GenParticle* theParticle, std::vector<const reco::GenParticle* >& container) 00130 { 00132 if (theParticle) 00133 { 00134 //edm::LogInfo("Debug") << "It's non-null"; 00135 int pdgId = std::abs(theParticle->pdgId()); 00136 //edm::LogInfo("Debug") << "PDGID = " << pdgId << " Status = " << theStatus; 00137 if (theParticle->status() == 1 || pdgId == 211 || pdgId == 111 || pdgId == 11 || pdgId == 13) 00138 { 00139 //edm::LogInfo("Debug") << "Adding to container..."; 00140 container.push_back(theParticle); 00141 //add neutral pions and this step.... 00142 if (pdgId == 111) 00143 genNeutralPions_.push_back(theParticle); 00144 } 00145 else 00146 { 00147 unsigned int nDaughters = theParticle->numberOfDaughters(); 00148 for (size_t dIter = 0; dIter < nDaughters; ++dIter) 00149 { 00150 const Candidate * daughter = theParticle->daughter(dIter); 00151 //edm::LogInfo("Debug") << "Recursing on daughter with PDG: " << daughter->pdgId(); 00152 GeneratorTau::decayToPDGClassification(static_cast<const reco::GenParticle*>(daughter), container); 00153 } 00154 00155 } 00156 } 00157 } 00158 00159 00160 void 00161 GeneratorTau::computeStableDecayProducts(const reco::GenParticle* theParticle, std::vector<const reco::GenParticle *>& container) 00162 { 00163 if (theParticle) 00164 { 00165 if (theParticle->status() == 1) //status = 1 indicates final state particle 00166 { 00167 //edm::LogInfo("GeneratorTau") << "computeStableDecayProducts: Found a final state daughter with status: " << theParticle->status() << " Num stable decay products so far: " << container.size(); 00168 container.push_back(theParticle); 00169 } 00170 else 00171 { 00172 unsigned int nDaughters = theParticle->numberOfDaughters(); 00173 for (size_t dIter = 0; dIter < nDaughters; ++dIter) 00174 { 00175 const Candidate * daughter = theParticle->daughter(dIter); 00176 //edm::LogInfo("Debug") << "Recursing on daughter with PDG: " << daughter->pdgId(); 00177 GeneratorTau::computeStableDecayProducts(static_cast<const reco::GenParticle*>(daughter), container); 00178 } 00179 } 00180 } 00181 } 00182 00183 GeneratorTau::GeneratorTau() 00184 { 00185 } 00186 00187 00188 void 00189 GeneratorTau::init() 00190 { 00191 //make sure this tau really decays 00192 theDecayMode_ = kUndefined; 00193 aFinalStateTau_ = false; 00194 00195 //get Decaymode 00196 //edm::LogInfo("GeneratorTau") << "Computing decay mode.."; 00197 theDecayMode_ = computeDecayMode(this); 00198 00199 //make sure it is a real tau decay 00200 if (theDecayMode_ != kUndefined) { 00201 aFinalStateTau_ = true; 00202 //edm::LogInfo("GeneratorTau") << "Found decay type: " << theDecayMode_ << ", computing stable decay products."; 00203 //get the stable decay products 00204 computeStableDecayProducts(this, stableDecayProducts_); 00205 //from the stable products, fill the lists 00206 //edm::LogInfo("GeneratorTau") << "Found " << stableDecayProducts_.size() << " stable decay products, filtering."; 00207 for (std::vector<const reco::GenParticle*>::const_iterator iter = stableDecayProducts_.begin(); 00208 iter != stableDecayProducts_.end(); 00209 ++iter) 00210 { 00211 //fill vectors 00212 int pdg_id = std::abs( (*iter)->pdgId() ); 00213 if (pdg_id == 16 || pdg_id == 12 || pdg_id == 14) 00214 genNus_.push_back( (*iter) ); 00215 else { 00216 visibleDecayProducts_.push_back( (*iter) ); 00217 if (pdg_id == 211 || (*iter)->charge() != 0) 00218 genChargedPions_.push_back( (*iter) ); 00219 else if (pdg_id == 22) 00220 genGammas_.push_back( (*iter) ); 00221 } 00222 } 00223 // find the lead charged object 00224 theLeadTrack_ = findLeadTrack(); 00225 } 00226 } 00227 00228 00229 00230 std::vector<LorentzVector> 00231 GeneratorTau::convertMCVectorToLorentzVectors( 00232 const std::vector<const reco::GenParticle*>& theList) const { 00233 std::vector<LorentzVector> output; 00234 std::vector<const reco::GenParticle*>::const_iterator theParticle; 00235 for (theParticle = theList.begin(); 00236 theParticle != theList.end(); ++theParticle) { 00237 output.push_back( (*theParticle)->p4() ); 00238 } 00239 return output; 00240 } 00241 00242 std::vector<const reco::Candidate*> 00243 GeneratorTau::getGenChargedPions() const { 00244 std::vector<const reco::Candidate*> output; 00245 std::vector<const GenParticle*>::const_iterator iter; 00246 for (iter = genChargedPions_.begin(); iter != genChargedPions_.end(); ++iter) 00247 output.push_back(static_cast<const reco::Candidate*>(*iter)); 00248 return output; 00249 } 00250 00251 std::vector<const reco::Candidate*> 00252 GeneratorTau::getGenNeutralPions() const { 00253 std::vector<const reco::Candidate*> output; 00254 std::vector<const GenParticle*>::const_iterator iter; 00255 for (iter = genNeutralPions_.begin(); iter != genNeutralPions_.end(); ++iter) 00256 output.push_back(static_cast<const reco::Candidate*>(*iter)); 00257 return output; 00258 } 00259 00260 std::vector<const reco::Candidate*> 00261 GeneratorTau::getGenGammas() const { 00262 std::vector<const reco::Candidate*> output; 00263 std::vector<const GenParticle*>::const_iterator iter; 00264 for (iter = genGammas_.begin(); iter != genGammas_.end(); ++iter) 00265 output.push_back(static_cast<const reco::Candidate*>(*iter)); 00266 return output; 00267 } 00268 00269 std::vector<const reco::Candidate*> 00270 GeneratorTau::getStableDecayProducts() const { 00271 std::vector<const reco::Candidate*> output; 00272 std::vector<const GenParticle*>::const_iterator iter; 00273 for (iter = stableDecayProducts_.begin(); 00274 iter != stableDecayProducts_.end(); ++iter) 00275 output.push_back(static_cast<const reco::Candidate*>(*iter)); 00276 return output; 00277 } 00278 00279 std::vector<const reco::Candidate*> GeneratorTau::getGenNu() const { 00280 std::vector<const reco::Candidate*> output; 00281 std::vector<const GenParticle*>::const_iterator iter; 00282 for (iter = genNus_.begin(); iter != genNus_.end(); ++iter) 00283 output.push_back(static_cast<const reco::Candidate*>(*iter)); 00284 return output; 00285 } 00286 00287 std::vector<LorentzVector> GeneratorTau::getChargedPions() const { 00288 return convertMCVectorToLorentzVectors(genChargedPions_); 00289 } 00290 00291 std::vector<LorentzVector> GeneratorTau::getGammas() const { 00292 return convertMCVectorToLorentzVectors(genGammas_); 00293 } 00294 00295 std::vector<LorentzVector> GeneratorTau::getVisibleFourVectors() const { 00296 return convertMCVectorToLorentzVectors(visibleDecayProducts_); 00297 } 00298 00299 LorentzVector GeneratorTau::getVisibleFourVector() const { 00300 LorentzVector output; 00301 std::vector<LorentzVector> tempForSum = getVisibleFourVectors(); 00302 for (std::vector<LorentzVector>::iterator iter = tempForSum.begin(); 00303 iter != tempForSum.end(); ++iter) 00304 output += (*iter); 00305 return output; 00306 } 00307