//============================================================================= // Return all descendants of level i for a Particle //============================================================================= const LHCb::Particle::ConstVector ParticleDescendants::descendants(const LHCb::Particle* P, int maxlevel){ LHCb::Particle::ConstVector Parts ; int level = 0 ; bool found = false ; LHCb::Particle::ConstVector mothers ; do { ++level ; LHCb::Particle::ConstVector leveldaughters ; if ( level == 1 ) found = addDaughters( P, leveldaughters) ; else found = addDaughters( mothers, leveldaughters) ; if ( level==maxlevel || maxlevel == 0 ) { Parts.insert(Parts.end(),leveldaughters.begin(),leveldaughters.end()) ; verbose() << "Level: " << level << " - inserted " << leveldaughters.size() << " daughters to get " << Parts.size() << endmsg ; } verbose() << "Level " << level << " of " << maxlevel << " : " << leveldaughters.size() << " daughters " << found << endmsg ; mothers = leveldaughters ; } while ( (maxlevel<=0 || level<=maxlevel) && found ) ; debug() << "Reached " << level << ". Returning " << Parts.size() << " daughters" << endmsg ; return Parts ; }
//============================================================================= // Return all daughters of particles in a vector //============================================================================= bool ParticleDescendants::addDaughters(const LHCb::Particle::ConstVector& mothers, LHCb::Particle::ConstVector& Parts){ if ( mothers.empty() ) return false ; bool found = false ; for ( LHCb::Particle::ConstVector::const_iterator i = mothers.begin() ; i!=mothers.end() ; ++i){ found = ( addDaughters( *i, Parts) || found ); } return found ; }
//============================================================================= // Return all stable descendants of a Particle //============================================================================= const LHCb::Particle::ConstVector ParticleDescendants::finalStates(const LHCb::Particle* P){ LHCb::Particle::ConstVector stables ; // LHCb::Particle::ConstVector all = descendants( P, 0 ); // get them all all for ( LHCb::Particle::ConstVector::const_iterator i = all.begin() ; i!=all.end() ; ++i){ if ( (*i)->isBasicParticle() ) { stables.push_back( *i ); debug() << "Saving a " << (*i)->particleID().pid() << endmsg ; } else verbose() << "Discarding a " << (*i)->particleID().pid() << endmsg ; } return stables; }
//============================================================================= // Return all daughters of particles in a vector //============================================================================= bool ParticleDescendants::addDaughters(const LHCb::Particle* M, LHCb::Particle::ConstVector& Parts){ if ( 0==M ) return false; if ( M->isBasicParticle() ) return false; const LHCb::Particle::ConstVector dauts = M->daughtersVector(); Parts.insert(Parts.end(),dauts.begin(),dauts.end()); verbose() << "Added " << dauts.size() << " daughters" << endmsg ; return (!dauts.empty()); }
//============================================================================= // Main execution //============================================================================= StatusCode B2DMuNu::execute() { if (msgLevel(MSG::DEBUG)) debug() << "==> Execute" << endmsg; StatusCode sc = StatusCode::SUCCESS; //### Extract Run number and Event number ###// const LHCb::ODIN* odin = get<LHCb::ODIN>(LHCb::ODINLocation::Default); const unsigned int runNum = odin->runNumber(), evNum = odin->eventNumber(); debug() << "Run number is " << runNum << " and Event ID is " << evNum << " at time " << odin->eventTime() << endmsg; //odin->gpsTime() << endmsg; counter("EventID")++; debug() << "### Processing event number " << counter("EventID").nEntries() << " in job ###" << endmsg; setFilterPassed(true); // Mandatory. Set to true if event is accepted. //### Only run on MC data if requested ###// if (m_runMC==1) { //### Test MC data to see if event warrants reconstruction (Require B0/B- OR B0~/B+ both decaying to muons) ###// m_passEvent = 0; debug() << "Performing Analysis on MC data" << endmsg; sc = loopOnMC(); if (!sc) return sc; } if (m_passEvent==1) { debug() << "### Event number " << counter("EventID").nEntries() << " accepted for analysis buddy ###" << endmsg; counter("EventPasses")++; debug() << "Extracting daughters..." << endmsg; LHCb::Particle::ConstVector daughters = this->i_particles(); if (daughters.size()!=0) { debug() << "### There are " << daughters.size() << " possible Muons in this event (EventID " << counter("EventID").nEntries() << ") ###" << endmsg; counter("MuonsPresent")++; //### Extract muon hits and muon misid if requested ###// if (m_muHits) { const std::string& strExtra = "Extra"; Extra* extra = new Extra(strExtra, m_local); Tuple fakeTuple = nTuple("fakeMuonTuple"); sc = extra->fakeMuon(daughters, fakeTuple); Tuple hitTuple = nTuple("muonHitTuple"); sc = extra->muonChamberHits(hitTuple); delete extra; if (!sc) return sc; } //### Test - Call loopOnRec ###// const std::string& strRec = "Rec"; Rec* rec = new Rec(strRec, m_local); Tuple recAllTuple=nTuple("recAllTuple"), hitDistTuple=nTuple("muHitDistTuple"), motherTuple=nTuple("motherTuple"), candTuple=nTuple("candidateTuple"); const LHCb::RecVertex::Range prims = this->primaryVertices(); LHCb::Particle::Vector mothers = rec->loopOnRec(daughters, prims, m_motherID, recAllTuple, hitDistTuple, motherTuple, candTuple, m_runMC); delete rec; if (!sc) return sc; } else debug() << "### There are no possible muons in the event!! ###" << endmsg; debug() << "### Finishing analysis for Event number " << counter("EventID").nEntries() << " ###" << endmsg; } else { debug() << "Event rejected" << endmsg; counter("EventFails")++; } debug() << "Event fully analysed." << endmsg; return StatusCode::SUCCESS; }