/
githubmirror
/
cmssw
Обзор
Документация
Войти
/
githubmirror
/
cmssw
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
master
DataFormats/ParticleFlowCandidate/src/PFCandidate.cc
676 строк
23 KB
Matti Kortelainen
Move stored types in io_v1 namespace, reset class versions to 3
22 май 2026, 18:18
22 май 2026, 18:18
909f324
Код
Авторство
О чём код?
#include "DataFormats/ParticleFlowCandidate/interface/PFCandidate.h" //#include "DataFormats/ParticleFlowReco/interface/PFBlock.h" #include "DataFormats/MuonReco/interface/Muon.h" #include "DataFormats/GsfTrackReco/interface/GsfTrack.h" #include "DataFormats/ParticleFlowReco/interface/PFDisplacedVertex.h" #include "DataFormats/ParticleFlowCandidate/interface/PFCandidateElectronExtra.h" #include "DataFormats/ParticleFlowCandidate/interface/PFCandidatePhotonExtra.h" #include "DataFormats/ParticleFlowCandidate/interface/PFCandidateEGammaExtra.h" #include "DataFormats/EgammaCandidates/interface/Conversion.h" #include "DataFormats/EgammaCandidates/interface/Photon.h" #include "FWCore/Utilities/interface/Exception.h" #include <ostream> #include <iomanip> using namespace reco; using namespace std; #include "DataFormats/ParticleFlowCandidate/src/CountBits.h" PFCandidate::PFCandidate() : elementsInBlocks_(nullptr), ecalERatio_(1.), hcalERatio_(1.), hoERatio_(1.), rawEcalEnergy_(0.), rawHcalEnergy_(0.), rawHoEnergy_(0.), ps1Energy_(0.), ps2Energy_(0.), flags_(0), deltaP_(0.), vertexType_(kCandVertex), mva_Isolated_(PFCandidate::bigMva_), mva_e_pi_(PFCandidate::bigMva_), mva_e_mu_(PFCandidate::bigMva_), mva_pi_mu_(PFCandidate::bigMva_), mva_nothing_gamma_(PFCandidate::bigMva_), mva_nothing_nh_(PFCandidate::bigMva_), mva_gamma_nh_(PFCandidate::bigMva_), dnn_e_sigIsolated_(PFCandidate::bigMva_), dnn_e_sigNonIsolated_(PFCandidate::bigMva_), dnn_e_bkgNonIsolated_(PFCandidate::bigMva_), dnn_e_bkgTau_(PFCandidate::bigMva_), dnn_e_bkgPhoton_(PFCandidate::bigMva_), dnn_gamma_(PFCandidate::bigMva_), getter_(nullptr), storedRefsBitPattern_(0), time_(0.f), timeError_(-1.f) { muonTrackType_ = reco::Muon::None; setPdgId(translateTypeToPdgId(X)); refsInfo_.reserve(3); std::fill(hcalDepthEnergyFractions_.begin(), hcalDepthEnergyFractions_.end(), 0.f); } const math::XYZPoint& PFCandidate::vertex() const { return vertexLegacy(vertexType_); } PFCandidate::PFCandidate(const PFCandidatePtr& sourcePtr) : PFCandidate(*sourcePtr) { sourcePtr_ = sourcePtr; hcalDepthEnergyFractions_ = sourcePtr->hcalDepthEnergyFractions_; // GP not sure it's needed } PFCandidate::PFCandidate(Charge charge, const LorentzVector& p4, ParticleType partId) : LeafCandidate(charge, p4), elementsInBlocks_(nullptr), ecalERatio_(1.), hcalERatio_(1.), hoERatio_(1.), rawEcalEnergy_(0.), rawHcalEnergy_(0.), rawHoEnergy_(0.), ps1Energy_(0.), ps2Energy_(0.), flags_(0), deltaP_(0.), vertexType_(kCandVertex), mva_Isolated_(PFCandidate::bigMva_), mva_e_pi_(PFCandidate::bigMva_), mva_e_mu_(PFCandidate::bigMva_), mva_pi_mu_(PFCandidate::bigMva_), mva_nothing_gamma_(PFCandidate::bigMva_), mva_nothing_nh_(PFCandidate::bigMva_), mva_gamma_nh_(PFCandidate::bigMva_), dnn_e_sigIsolated_(PFCandidate::bigMva_), dnn_e_sigNonIsolated_(PFCandidate::bigMva_), dnn_e_bkgNonIsolated_(PFCandidate::bigMva_), dnn_e_bkgTau_(PFCandidate::bigMva_), dnn_e_bkgPhoton_(PFCandidate::bigMva_), dnn_gamma_(PFCandidate::bigMva_), getter_(nullptr), storedRefsBitPattern_(0), time_(0.f), timeError_(-1.f) { refsInfo_.reserve(3); blocksStorage_.reserve(10); elementsStorage_.reserve(10); std::fill(hcalDepthEnergyFractions_.begin(), hcalDepthEnergyFractions_.end(), 0.f); muonTrackType_ = reco::Muon::None; // proceed with various consistency checks // charged candidate: track ref and charge must be non null if (partId == h || partId == e || partId == mu) { if (charge == 0) { string err; err += "Attempt to construct a charged PFCandidate with a zero charge"; throw cms::Exception("InconsistentValue", err.c_str()); } } else { if (charge) { string err; err += "Attempt to construct a neutral PFCandidate "; err += "with a non-zero charge"; throw cms::Exception("InconsistentValue", err.c_str()); } } setPdgId(translateTypeToPdgId(partId)); } PFCandidate::PFCandidate(PFCandidate const& iOther) : LeafCandidate(static_cast<LeafCandidate const&>(iOther)), elementsInBlocks_(nullptr), blocksStorage_(iOther.blocksStorage_), elementsStorage_(iOther.elementsStorage_), sourcePtr_(iOther.sourcePtr_), muonTrackType_(iOther.muonTrackType_), ecalERatio_(iOther.ecalERatio_), hcalERatio_(iOther.hcalERatio_), hoERatio_(iOther.hoERatio_), rawEcalEnergy_(iOther.rawEcalEnergy_), rawHcalEnergy_(iOther.rawHcalEnergy_), rawHoEnergy_(iOther.rawHoEnergy_), ps1Energy_(iOther.ps1Energy_), ps2Energy_(iOther.ps2Energy_), flags_(iOther.flags_), deltaP_(iOther.deltaP_), vertexType_(iOther.vertexType_), mva_Isolated_(iOther.mva_Isolated_), mva_e_pi_(iOther.mva_e_pi_), mva_e_mu_(iOther.mva_e_mu_), mva_pi_mu_(iOther.mva_pi_mu_), mva_nothing_gamma_(iOther.mva_nothing_gamma_), mva_nothing_nh_(iOther.mva_nothing_nh_), mva_gamma_nh_(iOther.mva_gamma_nh_), dnn_e_sigIsolated_(iOther.dnn_e_sigIsolated_), dnn_e_sigNonIsolated_(iOther.dnn_e_sigNonIsolated_), dnn_e_bkgNonIsolated_(iOther.dnn_e_bkgNonIsolated_), dnn_e_bkgTau_(iOther.dnn_e_bkgTau_), dnn_e_bkgPhoton_(iOther.dnn_e_bkgPhoton_), dnn_gamma_(iOther.dnn_gamma_), positionAtECALEntrance_(iOther.positionAtECALEntrance_), getter_(iOther.getter_), storedRefsBitPattern_(iOther.storedRefsBitPattern_), refsInfo_(iOther.refsInfo_), refsCollectionCache_(iOther.refsCollectionCache_), time_(iOther.time_), timeError_(iOther.timeError_), hcalDepthEnergyFractions_(iOther.hcalDepthEnergyFractions_) { auto tmp = iOther.elementsInBlocks_.load(std::memory_order_acquire); if (nullptr != tmp) { elementsInBlocks_.store(new ElementsInBlocks{*tmp}, std::memory_order_release); } } PFCandidate& PFCandidate::operator=(PFCandidate const& iOther) { LeafCandidate::operator=(iOther); auto tmp = iOther.elementsInBlocks_.load(std::memory_order_acquire); if (nullptr != tmp) { delete elementsInBlocks_.exchange(new ElementsInBlocks{*tmp}, std::memory_order_acq_rel); } else { delete elementsInBlocks_.exchange(nullptr, std::memory_order_acq_rel); } blocksStorage_ = iOther.blocksStorage_; elementsStorage_ = iOther.elementsStorage_; sourcePtr_ = iOther.sourcePtr_; muonTrackType_ = iOther.muonTrackType_; ecalERatio_ = iOther.ecalERatio_; hcalERatio_ = iOther.hcalERatio_; hoERatio_ = iOther.hoERatio_; rawEcalEnergy_ = iOther.rawEcalEnergy_; rawHcalEnergy_ = iOther.rawHcalEnergy_; rawHoEnergy_ = iOther.rawHoEnergy_; ps1Energy_ = iOther.ps1Energy_; ps2Energy_ = iOther.ps2Energy_; flags_ = iOther.flags_; deltaP_ = iOther.deltaP_; vertexType_ = iOther.vertexType_; mva_Isolated_ = iOther.mva_Isolated_; mva_e_pi_ = iOther.mva_e_pi_; mva_e_mu_ = iOther.mva_e_mu_; mva_pi_mu_ = iOther.mva_pi_mu_; mva_nothing_gamma_ = iOther.mva_nothing_gamma_; mva_nothing_nh_ = iOther.mva_nothing_nh_; mva_gamma_nh_ = iOther.mva_gamma_nh_; dnn_e_sigIsolated_ = iOther.dnn_e_sigIsolated_; dnn_e_sigNonIsolated_ = iOther.dnn_e_sigNonIsolated_; dnn_e_bkgNonIsolated_ = iOther.dnn_e_bkgNonIsolated_; dnn_e_bkgTau_ = iOther.dnn_e_bkgTau_; dnn_e_bkgPhoton_ = iOther.dnn_e_bkgPhoton_; dnn_gamma_ = iOther.dnn_gamma_; positionAtECALEntrance_ = iOther.positionAtECALEntrance_; getter_ = iOther.getter_; storedRefsBitPattern_ = iOther.storedRefsBitPattern_; refsInfo_ = iOther.refsInfo_; refsCollectionCache_ = iOther.refsCollectionCache_; time_ = iOther.time_; timeError_ = iOther.timeError_; hcalDepthEnergyFractions_ = iOther.hcalDepthEnergyFractions_; return *this; } PFCandidate::~PFCandidate() { delete elementsInBlocks_.load(std::memory_order_acquire); } PFCandidate* PFCandidate::clone() const { return new PFCandidate(*this); } void PFCandidate::addElementInBlock(const reco::PFBlockRef& blockref, unsigned elementIndex) { //elementsInBlocks_.push_back( make_pair(blockref.key(), elementIndex) ); if (blocksStorage_.empty()) blocksStorage_ = Blocks(blockref.id()); blocksStorage_.push_back(blockref); elementsStorage_.push_back(elementIndex); auto ptr = elementsInBlocks_.exchange(nullptr); delete ptr; } PFCandidate::ParticleType PFCandidate::translatePdgIdToType(int pdgid) const { switch (std::abs(pdgid)) { case 211: return h; case 11: return e; case 13: return mu; case 22: return gamma; case 130: return h0; case 1: return h_HF; case 2: return egamma_HF; case 0: return X; default: return X; } } int PFCandidate::translateTypeToPdgId(ParticleType type) const { int thecharge = charge(); switch (type) { case h: return thecharge * 211; // pi+ case e: return thecharge * (-11); case mu: return thecharge * (-13); case gamma: return 22; case h0: return 130; // K_L0 case h_HF: return 1; // dummy pdg code case egamma_HF: return 2; // dummy pdg code case X: default: return 0; } } void PFCandidate::setParticleType(ParticleType type) { setPdgId(translateTypeToPdgId(type)); } bool PFCandidate::overlap(const reco::Candidate& other) const { CandidatePtr myPtr = sourceCandidatePtr(0); if (myPtr.isNull()) return false; for (size_t i = 0, n = other.numberOfSourceCandidatePtrs(); i < n; ++i) { CandidatePtr otherPtr = other.sourceCandidatePtr(i); if ((otherPtr == myPtr) || (sourcePtr_.isNonnull() && otherPtr.isNonnull() && sourcePtr_->overlap(*otherPtr))) { return true; } } return false; } // Rescale three-momentum, preserving mass void PFCandidate::rescaleMomentum(double rescaleFactor) { if (rescaleFactor < 0) throw cms::Exception( "NegativeScaling", "Scale factor " + std::to_string(rescaleFactor) + " is < 0. Cannot rescale momentum by this value"); float e = std::sqrt(p() * p() * rescaleFactor * rescaleFactor + mass() * mass()); LorentzVector rescaledp4(rescaleFactor * px(), rescaleFactor * py(), rescaleFactor * pz(), e); setP4(rescaledp4); } void PFCandidate::setFlag(Flags theFlag, bool value) { if (value) flags_ = flags_ | (1 << theFlag); else flags_ = flags_ ^ (1 << theFlag); } bool PFCandidate::flag(Flags theFlag) const { return (flags_ >> theFlag) & 1; } ostream& reco::io_v1::operator<<(ostream& out, const PFCandidate& c) { if (!out) return out; out << "\tPFCandidate type: " << c.particleId(); out << setiosflags(ios::right); out << setiosflags(ios::fixed); out << setprecision(3); out << " E/pT/eta/phi " << c.energy() << "/" << c.pt() << "/" << c.eta() << "/" << c.phi(); if (c.flag(PFCandidate::T_FROM_DISP)) out << ", T_FROM_DISP" << endl; else if (c.flag(PFCandidate::T_TO_DISP)) out << ", T_TO_DISP" << endl; else if (c.flag(PFCandidate::T_FROM_GAMMACONV)) out << ", T_FROM_GAMMACONV" << endl; else if (c.flag(PFCandidate::GAMMA_TO_GAMMACONV)) out << ", GAMMA_TO_GAMMACONV" << endl; out << ", blocks/iele: "; const PFCandidate::ElementsInBlocks& eleInBlocks = c.elementsInBlocks(); for (unsigned i = 0; i < eleInBlocks.size(); i++) { PFBlockRef blockRef = eleInBlocks[i].first; unsigned indexInBlock = eleInBlocks[i].second; out << "(" << blockRef.key() << "|" << indexInBlock << "), "; } out << " source:" << c.sourcePtr_.id() << "/" << c.sourcePtr_.key(); // PFBlockRef blockRef = c.block(); // int blockid = blockRef.key(); // const edm::OwnVector< reco::PFBlockElement >& elements = c.elements(); // out<< "\t# of elements " << elements.size() // <<" from block " << blockid << endl; // // print each element in turn // for(unsigned ie=0; ie<elements.size(); ie++) { // out<<"\t"<< elements[ie] <<endl; // } // Improved printout for electrons if PFCandidateElectronExtra is available if (c.particleId() == PFCandidate::e && c.electronExtraRef().isNonnull() && c.electronExtraRef().isAvailable()) { out << std::endl << *(c.electronExtraRef()); } out << resetiosflags(ios::right | ios::fixed); return out; } static unsigned long long bitPackRefInfo(const edm::RefCore& iCore, size_t iIndex) { unsigned long long bitPack = iIndex; bitPack |= static_cast<unsigned long long>(iCore.id().productIndex()) << 32; bitPack |= static_cast<unsigned long long>(iCore.id().processIndex()) << 48; return bitPack; } void PFCandidate::storeRefInfo(unsigned int iMask, unsigned int iBit, bool iIsValid, const edm::RefCore& iCore, size_t iKey, const edm::EDProductGetter* iGetter) { size_t index = s_refsBefore[storedRefsBitPattern_ & iMask]; if (nullptr == getter_) { getter_ = iGetter; } if (iIsValid) { if (0 == (storedRefsBitPattern_ & iBit)) { refsInfo_.insert(refsInfo_.begin() + index, bitPackRefInfo(iCore, iKey)); if (iGetter == nullptr) refsCollectionCache_.insert(refsCollectionCache_.begin() + index, static_cast<void const*>(iCore.productPtr())); else refsCollectionCache_.insert(refsCollectionCache_.begin() + index, nullptr); } else { assert(refsInfo_.size() > index); *(refsInfo_.begin() + index) = bitPackRefInfo(iCore, iKey); if (iGetter == nullptr) *(refsCollectionCache_.begin() + index) = static_cast<void const*>(iCore.productPtr()); else *(refsCollectionCache_.begin() + index) = nullptr; } storedRefsBitPattern_ |= iBit; } else { if (storedRefsBitPattern_ & iBit) { refsInfo_.erase(refsInfo_.begin() + index); refsCollectionCache_.erase(refsCollectionCache_.begin() + index); storedRefsBitPattern_ ^= iBit; } } } bool PFCandidate::getRefInfo( unsigned int iMask, unsigned int iBit, edm::ProductID& oProductID, size_t& oIndex, size_t& aIndex) const { if (0 == (iBit & storedRefsBitPattern_)) { return false; } aIndex = s_refsBefore[storedRefsBitPattern_ & iMask]; unsigned long long bitPacked = refsInfo_[aIndex]; oIndex = bitPacked & 0xFFFFFFFFULL; //low 32 bits are the index unsigned short productIndex = (bitPacked & 0x0000FFFF00000000ULL) >> 32; unsigned short processIndex = (bitPacked & 0xFFFF000000000000ULL) >> 48; oProductID = edm::ProductID(processIndex, productIndex); return true; } void PFCandidate::setTrackRef(const reco::TrackRef& iRef) { if (!charge()) { string err; err += "PFCandidate::setTrackRef: this is a neutral candidate! "; err += "particleId_="; char num[4]; sprintf(num, "%d", particleId()); err += num; throw cms::Exception("InconsistentReference", err.c_str()); } storeRefInfo(kRefTrackMask, kRefTrackBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::TrackRef PFCandidate::trackRef() const { GETREF(reco::Track, kRefTrackMask, kRefTrackBit); } void PFCandidate::setMuonRef(reco::MuonRef const& iRef) { if (trackRef() != iRef->track()) { string err; err += "PFCandidate::setMuonRef: inconsistent track references!"; throw cms::Exception("InconsistentReference", err.c_str()); } storeRefInfo(kRefMuonMask, kRefMuonBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::MuonRef PFCandidate::muonRef() const { GETREF(reco::Muon, kRefMuonMask, kRefMuonBit); } ////////////// void PFCandidate::setGsfTrackRef(reco::GsfTrackRef const& iRef) { // Removed by F. Beaudette. Would like to be able to save the GsfTrackRef even for charged pions // if( particleId() != e ) { // string err; // err += "PFCandidate::setGsfTrackRef: this is not an electron ! particleId_="; // char num[4]; // sprintf( num, "%d", particleId()); // err += num; // // throw cms::Exception("InconsistentReference", // err.c_str() ); // } storeRefInfo(kRefGsfTrackMask, kRefGsfTrackBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::GsfTrackRef PFCandidate::gsfTrackRef() const { GETREF(reco::GsfTrack, kRefGsfTrackMask, kRefGsfTrackBit); } ////////////// void PFCandidate::setDisplacedVertexRef(const reco::PFDisplacedVertexRef& iRef, Flags type) { if (particleId() != h) { string err; err += "PFCandidate::setDisplacedVertexRef: this is not a hadron! particleId_="; char num[4]; sprintf(num, "%d", particleId()); err += num; throw cms::Exception("InconsistentReference", err.c_str()); } else if (!flag(T_FROM_DISP) && !flag(T_TO_DISP)) { string err; err += "PFCandidate::setDisplacedVertexRef: particule flag is neither T_FROM_DISP nor T_TO_DISP"; throw cms::Exception("InconsistentReference", err.c_str()); } if (type == T_TO_DISP && flag(T_TO_DISP)) storeRefInfo(kRefDisplacedVertexDauMask, kRefDisplacedVertexDauBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); else if (type == T_FROM_DISP && flag(T_FROM_DISP)) storeRefInfo(kRefDisplacedVertexMotMask, kRefDisplacedVertexMotBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); else if ((type == T_FROM_DISP && !flag(T_FROM_DISP)) || (type == T_TO_DISP && !flag(T_TO_DISP))) { string err; err += "PFCandidate::setDisplacedVertexRef: particule flag is not switched on"; throw cms::Exception("InconsistentReference", err.c_str()); } } reco::PFDisplacedVertexRef PFCandidate::displacedVertexRef(Flags type) const { if (type == T_TO_DISP) { GETREF(reco::PFDisplacedVertex, kRefDisplacedVertexDauMask, kRefDisplacedVertexDauBit); } else if (type == T_FROM_DISP) { GETREF(reco::PFDisplacedVertex, kRefDisplacedVertexMotMask, kRefDisplacedVertexMotBit); } return reco::PFDisplacedVertexRef(); } ////////////// void PFCandidate::setConversionRef(reco::ConversionRef const& iRef) { if (particleId() != gamma) { string err; err += "PFCandidate::setConversionRef: this is not a (converted) photon ! particleId_="; char num[4]; sprintf(num, "%d", particleId()); err += num; throw cms::Exception("InconsistentReference", err.c_str()); } else if (!flag(GAMMA_TO_GAMMACONV)) { string err; err += "PFCandidate::setConversionRef: particule flag is not GAMMA_TO_GAMMACONV"; throw cms::Exception("InconsistentReference", err.c_str()); } storeRefInfo( kRefConversionMask, kRefConversionBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::ConversionRef PFCandidate::conversionRef() const { GETREF(reco::Conversion, kRefConversionMask, kRefConversionBit); } ////////////// void PFCandidate::setV0Ref(reco::VertexCompositeCandidateRef const& iRef) { storeRefInfo(kRefV0Mask, kRefV0Bit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::VertexCompositeCandidateRef PFCandidate::v0Ref() const { GETREF(reco::VertexCompositeCandidate, kRefV0Mask, kRefV0Bit); } ////////////// void PFCandidate::setGsfElectronRef(reco::GsfElectronRef const& iRef) { storeRefInfo( kRefGsfElectronMask, kRefGsfElectronBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::GsfElectronRef PFCandidate::gsfElectronRef() const { GETREF(reco::GsfElectron, kRefGsfElectronMask, kRefGsfElectronBit); } ////////////// void PFCandidate::setPFElectronExtraRef(reco::PFCandidateElectronExtraRef const& iRef) { storeRefInfo(kRefPFElectronExtraMask, kRefPFElectronExtraBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } reco::PFCandidateElectronExtraRef PFCandidate::electronExtraRef() const { GETREF(reco::PFCandidateElectronExtra, kRefPFElectronExtraMask, kRefPFElectronExtraBit); } reco::PhotonRef PFCandidate::photonRef() const { GETREF(reco::Photon, kRefPhotonMask, kRefPhotonBit); } reco::PFCandidatePhotonExtraRef PFCandidate::photonExtraRef() const { GETREF(reco::PFCandidatePhotonExtra, kRefPFPhotonExtraMask, kRefPFPhotonExtraBit); } reco::PFCandidateEGammaExtraRef PFCandidate::egammaExtraRef() const { GETREF(reco::PFCandidateEGammaExtra, kRefPFEGammaExtraMask, kRefPFEGammaExtraBit); } reco::SuperClusterRef PFCandidate::superClusterRef() const { GETREF(reco::SuperCluster, kRefSuperClusterMask, kRefSuperClusterBit); } void PFCandidate::setPhotonRef(const reco::PhotonRef& iRef) { if (particleId() != gamma && particleId() != e) { string err; err += "PFCandidate::setSuperClusterRef: this is not an electron neither a photon ! particleId_="; char num[4]; sprintf(num, "%d", particleId()); err += num; throw cms::Exception("InconsistentReference", err.c_str()); } storeRefInfo(kRefPhotonMask, kRefPhotonBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } void PFCandidate::setSuperClusterRef(const reco::SuperClusterRef& iRef) { if (particleId() != gamma && particleId() != e) { string err; err += "PFCandidate::setSuperClusterRef: this is not an electron neither a photon ! particleId_="; char num[4]; sprintf(num, "%d", particleId()); err += num; throw cms::Exception("InconsistentReference", err.c_str()); } storeRefInfo( kRefSuperClusterMask, kRefSuperClusterBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } void PFCandidate::setPFPhotonExtraRef(const reco::PFCandidatePhotonExtraRef& iRef) { storeRefInfo( kRefPFPhotonExtraMask, kRefPFPhotonExtraBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } void PFCandidate::setPFEGammaExtraRef(const reco::PFCandidateEGammaExtraRef& iRef) { storeRefInfo( kRefPFEGammaExtraMask, kRefPFEGammaExtraBit, iRef.isNonnull(), iRef.refCore(), iRef.key(), iRef.productGetter()); } const math::XYZPoint& PFCandidate::vertexLegacy(PFCandidate::PFVertexType vertexType) const { switch (vertexType) { case kCandVertex: return LeafCandidate::vertex(); break; //the following cases will only be called for legacy AOD which does not have an embedded vertex case kTrkVertex: return trackRef()->vertex(); break; case kComMuonVertex: return muonRef()->combinedMuon()->vertex(); break; case kSAMuonVertex: return muonRef()->standAloneMuon()->vertex(); break; case kTrkMuonVertex: return muonRef()->track()->vertex(); break; case kTPFMSMuonVertex: return muonRef()->tpfmsTrack()->vertex(); break; case kPickyMuonVertex: return muonRef()->pickyTrack()->vertex(); break; case kDYTMuonVertex: return muonRef()->dytTrack()->vertex(); break; case kGSFVertex: return gsfTrackRef()->vertex(); break; } return LeafCandidate::vertex(); } const PFCandidate::ElementsInBlocks& PFCandidate::elementsInBlocks() const { if (nullptr == elementsInBlocks_.load(std::memory_order_acquire)) { std::unique_ptr<ElementsInBlocks> temp(new ElementsInBlocks(blocksStorage_.size())); for (unsigned int icopy = 0; icopy != blocksStorage_.size(); ++icopy) (*temp)[icopy] = std::make_pair(blocksStorage_[icopy], elementsStorage_[icopy]); ElementsInBlocks* expected = nullptr; if (elementsInBlocks_.compare_exchange_strong(expected, temp.get(), std::memory_order_acq_rel)) { temp.release(); } } return *(elementsInBlocks_.load(std::memory_order_acquire)); }