35 #include "TMVA/MethodBDT.h" 38 #include "combination.hpp" 44 #define docast(x,y) dynamic_cast<x>(y) 45 #define LOGVERB(x) edm::LogVerbatim(x) 46 #define LOGWARN(x) edm::LogWarning(x) 47 #define LOGERR(x) edm::LogError(x) 48 #define LOGDRESSED(x) edm::LogInfo(x) 50 #define docast(x,y) reinterpret_cast<x>(y) 51 #define LOGVERB(x) LogTrace(x) 52 #define LOGWARN(x) edm::LogWarning(x) 53 #define LOGERR(x) edm::LogError(x) 54 #define LOGDRESSED(x) LogDebug(x) 63 typedef std::pair<CaloClusterPtr::key_type,CaloClusterPtr> EEtoPSElement;
71 typedef std::unary_function<
const ClusterFlaggedElement&,
74 typedef std::unary_function<
const PFFlaggedElement&,
75 bool> PFFlaggedElementMatcher;
76 typedef std::binary_function<
const PFFlaggedElement&,
77 const PFFlaggedElement&,
78 bool> PFFlaggedElementSorter;
81 bool> PFElementMatcher;
86 typedef std::unary_function<PFFlaggedElement&,
87 ClusterFlaggedElement> ClusterElementConverter;
89 struct SumPSEnergy :
public std::binary_function<double,
90 const ClusterFlaggedElement&,
94 double operator()(
double a,
95 const ClusterFlaggedElement&
b) {
97 return a + (_thetype == b.first->type())*b.first->clusterRef()->energy();
101 bool comparePSMapByKey(
const EEtoPSElement&
a,
102 const EEtoPSElement&
b) {
103 return a.first < b.first;
106 struct UsableElementToPSCluster :
public ClusterElementConverter {
107 ClusterFlaggedElement operator () (PFFlaggedElement&
elem) {
108 const ClusterElement* pselemascluster =
109 docast(
const ClusterElement*,elem.first);
112 std::stringstream ps_err;
113 pselemascluster->Dump(ps_err,
"\t");
115 <<
"This element is not a PS cluster!" << std::endl
116 << ps_err.str() << std::endl;
118 if( elem.second ==
false ) {
119 std::stringstream ps_err;
120 pselemascluster->Dump(ps_err,
"\t");
122 <<
"PS Cluster matched to EE is already used! " 123 <<
"This should be impossible!" << std::endl
124 << ps_err.str() << std::endl;
127 return std::make_pair(pselemascluster,
true);
131 struct SeedMatchesToSCElement :
public PFFlaggedElementMatcher {
136 bool operator() (
const PFFlaggedElement&
elem) {
137 const SCElement* scelem =
docast(
const SCElement*,elem.first);
138 if( _scfromseed.
isNull() || !elem.second || !scelem)
return false;
139 return ( _scfromseed->seed()->seed() ==
140 scelem->superClusterRef()->seed()->seed() );
144 struct SCSubClusterMatchesToElement :
public PFFlaggedElementMatcher {
150 bool operator() (
const PFFlaggedElement&
elem) {
151 const ClusterElement* cluselem =
152 docast(
const ClusterElement*,elem.first);
153 if( !elem.second || !cluselem)
return false;
155 for( ; cl !=
end; ++
cl ) {
156 if((*cl)->seed() == cluselem->clusterRef()->seed()) {
164 struct SeedMatchesToProtoObject :
public POMatcher {
175 bool operator() (
const PFEGammaAlgo::ProtoEGObject& po) {
178 return ( _scfromseed->seed() ==
181 return ( _scfromseed->seed()->seed() ==
186 template<
bool useConvs=false>
192 const float EoPin_cut = 1.0e6) {
201 &(block->elements()[
key]));
203 const ClusterElement* elemasclus =
204 reinterpret_cast<const ClusterElement*
>(&(block->elements()[
test]));
205 float cluster_e = elemasclus->clusterRef()->correctedEnergy();
206 float trk_pin = elemasgsf->
Pin().P();
207 if( cluster_e / trk_pin > EoPin_cut ) {
209 <<
"GSF track failed EoP cut to match with cluster!";
219 &(block->elements()[
key]));
221 const ClusterElement* elemasclus =
222 reinterpret_cast<const ClusterElement*
>(&(block->elements()[
test]));
223 float cluster_e = elemasclus->clusterRef()->correctedEnergy();
226 if( cluster_e / trk_pin > EoPin_cut ) {
228 <<
"KF track failed EoP cut to match with cluster!";
240 if( dist == -1.0
f )
return false;
241 std::multimap<double, unsigned> dists_to_val;
242 block->associatedElements(test,block->linkData(),dists_to_val,keytype,
245 for(
const auto& valdist : dists_to_val ) {
246 const size_t idx = valdist.second;
253 &(block->elements()[
idx]));
254 if( !useConvs && elemasgsf->
trackType(ConvType) )
return false;
256 const ClusterElement* elemasclus =
257 docast(
const ClusterElement*,&(block->elements()[
test]));
258 float cluster_e = elemasclus->clusterRef()->correctedEnergy();
259 float trk_pin = elemasgsf->
Pin().P();
260 if( cluster_e / trk_pin > EoPin_cut )
continue;
268 &(block->elements()[
idx]));
269 if( !useConvs && elemaskf->
trackType(ConvType) )
return false;
271 const ClusterElement* elemasclus =
272 reinterpret_cast<const ClusterElement*
>(&(block->elements()[
test]));
273 float cluster_e = elemasclus->clusterRef()->correctedEnergy();
276 if( cluster_e / trk_pin > EoPin_cut )
continue;
283 if( valdist.first < dist && idx != key ) {
285 <<
"key element of type " << keytype
286 <<
" is closer to another element of type" << valtype
294 struct CompatibleEoPOut :
public PFFlaggedElementMatcher {
297 bool operator()(
const PFFlaggedElement&
e)
const {
299 const ClusterElement* elemascluster =
300 docast(
const ClusterElement*,e.first);
304 return ( gsf_eta_diff <= 0.3 && cRef->energy()/comp->
Pout().t() <= 5 );
308 template<
class TrackElementType>
309 struct IsConversionTrack : PFFlaggedElementMatcher {
310 bool operator()(
const PFFlaggedElement&
e) {
313 const TrackElementType* elemastrk =
314 docast(
const TrackElementType*,e.first);
315 return elemastrk->trackType(ConvType);
322 struct NotCloserToOther :
public PFFlaggedElementMatcher {
323 const reco::PFBlockElement*
comp;
326 const float EoPin_cut;
329 const PFFlaggedElement*
e,
330 const float EoPcut=1.0e6):
comp(e->first),
337 const reco::PFBlockElement* e,
338 const float EoPcut=1.0e6):
comp(e),
343 bool operator () (
const PFFlaggedElement& e) {
344 if( !e.second || valtype != e.first->type() )
return false;
345 return elementNotCloserToOther<useConv>(
block,
346 keytype,comp->
index(),
347 valtype,e.first->index(),
352 struct LesserByDistance :
public PFFlaggedElementSorter {
353 const reco::PFBlockElement*
comp;
358 const PFFlaggedElement*
e):
comp(e->first),
363 const reco::PFBlockElement* e):
comp(e),
366 bool operator () (
const PFFlaggedElement&
e1,
367 const PFFlaggedElement&
e2) {
368 double dist1 = block->dist(comp->
index(),
372 double dist2 = block->dist(comp->
index(),
376 dist1 = ( dist1 == -1.0 ? 1e6 : dist1 );
377 dist2 = ( dist2 == -1.0 ? 1e6 : dist2 );
378 return dist1 < dist2;
382 bool isROLinkedByClusterOrTrack(
const PFEGammaAlgo::ProtoEGObject& RO1,
383 const PFEGammaAlgo::ProtoEGObject& RO2 ) {
388 <<
"cannot merge, both have GSFs!" << std::endl;
393 if(RO1.
ecalclusters.front().first->clusterRef()->layer() !=
394 RO2.
ecalclusters.front().first->clusterRef()->layer() ) {
396 <<
"cannot merge, different ECAL types!" << std::endl;
406 elementNotCloserToOther(blk,
407 cluster.first->type(),
408 cluster.first->
index(),
409 primgsf.first->type(),
410 primgsf.first->index());
413 <<
"merged by cluster to primary GSF" << std::endl;
417 <<
"cluster to primary GSF failed since" 418 <<
" cluster closer to another GSF" << std::endl;
423 elementNotCloserToOther(blk,
424 cluster.first->type(),
425 cluster.first->
index(),
426 primkf.first->type(),
427 primkf.first->index());
430 <<
"merged by cluster to primary KF" << std::endl;
436 elementNotCloserToOther(blk,
437 cluster.first->type(),
438 cluster.first->
index(),
439 secdkf.first->type(),
440 secdkf.first->index());
443 <<
"merged by cluster to secondary KF" << std::endl;
448 for(
const auto& brem : RO2.
brems ) {
449 not_closer = elementNotCloserToOther(blk,
450 cluster.first->type(),
451 cluster.first->
index(),
453 brem.first->index());
456 <<
"merged by cluster to brem KF" << std::endl;
465 elementNotCloserToOther(blk,
466 primgsf.first->type(),
467 primgsf.first->
index(),
468 secdkf.first->type(),
469 secdkf.first->index());
472 <<
"merged by GSF to secondary KF" << std::endl;
481 elementNotCloserToOther(blk,
482 primkf.first->type(),
483 primkf.first->
index(),
484 secdkf.first->type(),
485 secdkf.first->index());
488 <<
"merged by primary KF to secondary KF" << std::endl;
497 elementNotCloserToOther<true>(blk,
498 secdkf1.first->type(),
499 secdkf1.first->
index(),
500 secdkf2.first->type(),
501 secdkf2.first->index());
504 <<
"merged by secondary KF to secondary KF" << std::endl;
512 struct TestIfROMergableByLink :
public POMatcher {
513 const PFEGammaAlgo::ProtoEGObject&
comp;
514 TestIfROMergableByLink(
const PFEGammaAlgo::ProtoEGObject& RO) :
516 bool operator() (
const PFEGammaAlgo::ProtoEGObject& ro) {
517 const bool result = ( isROLinkedByClusterOrTrack(comp,ro) ||
518 isROLinkedByClusterOrTrack(ro,comp) );
523 std::vector<const ClusterElement*>
525 std::vector<PFFlaggedElement>& ecals) {
526 std::vector<const ClusterElement*> cluster_list;
527 auto sccl = scref->clustersBegin();
528 auto scend = scref->clustersEnd();
529 auto pfc = ecals.begin();
530 auto pfcend = ecals.end();
531 for( ; sccl != scend; ++sccl ) {
532 std::vector<const ClusterElement*> matched_pfcs;
533 const double eg_energy = (*sccl)->energy();
535 for( pfc = ecals.begin(); pfc != pfcend; ++pfc ) {
536 const ClusterElement *pfcel =
537 docast(
const ClusterElement*, pfc->first);
542 if( matched && pfcel->clusterRef()->energy() < 1.2*scref->energy()) {
543 matched_pfcs.push_back(pfcel);
546 std::sort(matched_pfcs.begin(),matched_pfcs.end());
548 double min_residual = 1e6;
549 std::vector<const ClusterElement*> best_comb;
550 for(
size_t i = 1;
i <= matched_pfcs.size(); ++
i ) {
555 double energy = std::accumulate(matched_pfcs.begin(),
556 matched_pfcs.begin()+
i,
559 const ClusterElement*
c)
560 {
return a +
c->clusterRef()->energy(); });
561 const double resid =
std::abs(energy - eg_energy);
562 if( resid < min_residual ) {
564 best_comb.reserve(
i);
565 min_residual = resid;
566 best_comb.insert(best_comb.begin(),
567 matched_pfcs.begin(),
568 matched_pfcs.begin()+
i);
571 matched_pfcs.begin()+
i,
572 matched_pfcs.end()));
574 for(
const auto& clelem : best_comb ) {
575 if(
std::find(cluster_list.begin(),cluster_list.end(),clelem) ==
576 cluster_list.end() ) {
577 cluster_list.push_back(clelem);
583 bool addPFClusterToROSafe(
const ClusterElement*
cl,
584 PFEGammaAlgo::ProtoEGObject& RO) {
592 if( clayer == blayer ) {
602 void setROElectronCluster(PFEGammaAlgo::ProtoEGObject& RO) {
609 *kfCluster =
nullptr, *gsfCluster_noassc =
nullptr;
611 int nBremClusters = 0;
613 float mDist_gsf(maxDist), mDist_gsf_noassc(maxDist), mDist_kf(maxDist);
616 const bool hasclu = elementNotCloserToOther(parent,
619 cluster.first->type(),
620 cluster.first->index());
622 std::abs(cluster.first->clusterRef()->positionREP().eta() -
623 gsf.first->positionAtECALEntrance().eta());
626 cluster.first->clusterRef()->positionREP().phi() -
627 gsf.first->positionAtECALEntrance().phi()));
628 const float dist = std::hypot(deta,dphi);
629 if( hasclu && dist < mDist_gsf ) {
630 gsfCluster = cluster.first;
632 }
else if ( dist < mDist_gsf_noassc ) {
633 gsfCluster_noassc = cluster.first;
634 mDist_gsf_noassc = dist;
638 const bool hasclu = elementNotCloserToOther(parent,
641 cluster.first->type(),
642 cluster.first->index());
643 const float dist = parent->dist(cluster.first->index(),
647 if( hasclu && dist < mDist_kf ) {
648 kfCluster = cluster.first;
652 for(
const auto& brem : RO.
brems ) {
653 const bool hasclu = elementNotCloserToOther(parent,
656 cluster.first->type(),
657 cluster.first->index());
662 brem.first->indTrajPoint() - 2) ) {
663 firstBrem = brem.first;
666 ( lastBrem->indTrajPoint() - 2 <
667 brem.first->indTrajPoint() - 2) ) {
668 lastBrem = brem.first;
669 bremCluster = cluster.first;
674 if( !gsfCluster && !kfCluster && !bremCluster ) {
675 gsfCluster = gsfCluster_noassc;
681 }
else if ( kfCluster ) {
684 if( bremCluster && !gsfCluster && !kfCluster ) {
689 if( bremCluster == gsfCluster ) RO.
lateBrem = 1;
700 chi2(0.0), STIP(0.0), del_phi(0.0),HoverPt(0.0), EoverPt(0.0), track_pt(0.0),
702 CrysPhi_(0.0), CrysEta_(0.0), VtxZ_(0.0), ClusPhi_(0.0), ClusEta_(0.0),
703 ClusR9_(0.0), Clus5x5ratio_(0.0), PFCrysEtaCrack_(0.0), logPFClusE_(0.0), e3x3_(0.0),
704 CrysIPhi_(0), CrysIEta_(0),
705 CrysX_(0.0), CrysY_(0.0),
707 eSeed_(0.0), e1x3_(0.0),e3x1_(0.0), e1x5_(0.0), e2x5Top_(0.0), e2x5Bottom_(0.0), e2x5Left_(0.0), e2x5Right_(0.0),
708 etop_(0.0), ebottom_(0.0), eleft_(0.0), eright_(0.0),
710 PFPhoEta_(0.0), PFPhoPhi_(0.0), PFPhoR9_(0.0), PFPhoR9Corr_(0.0), SCPhiWidth_(0.0), SCEtaWidth_(0.0),
711 PFPhoEt_(0.0), RConv_(0.0), PFPhoEtCorr_(0.0), PFPhoE_(0.0), PFPhoECorr_(0.0), MustE_(0.0), E3x3_(0.0),
712 dEta_(0.0), dPhi_(0.0), LowClusE_(0.0), RMSAll_(0.0), RMSMust_(0.0), nPFClus_(0.0),
713 TotPS1_(0.0), TotPS2_(0.0),
715 x0inner_(0.0), x0middle_(0.0), x0outer_(0.0),
716 excluded_(0.0), Mustache_EtRatio_(0.0), Mustache_Et_out_(0.0),
720 TFile *XO_File =
new TFile(
cfg_.
X0_Map.c_str(),
"READ");
721 X0_sum = (TH2D*)XO_File->Get(
"TrackerSum");
722 X0_inner = (TH2D*)XO_File->Get(
"Inner");
723 X0_middle = (TH2D*)XO_File->Get(
"Middle");
724 X0_outer = (TH2D*)XO_File->Get(
"Outer");
730 std::vector<bool>& active) {
749 unsigned int track_index) {
755 chi2=elements[track_index].trackRef()->chi2()/elements[track_index].trackRef()->ndof();
756 nlost=elements[track_index].trackRef()->hitPattern().numberOfLostHits(HitPattern::MISSING_INNER_HITS);
757 nlayers=elements[track_index].trackRef()->hitPattern().trackerLayersWithMeasurement();
758 track_pt=elements[track_index].trackRef()->pt();
759 STIP=elements[track_index].trackRefPF()->STIP();
763 std::multimap<double, unsigned int> ecalAssoTrack;
768 std::multimap<double, unsigned int> hcalAssoTrack;
773 if(!ecalAssoTrack.empty()) {
774 for(std::multimap<double, unsigned int>::iterator itecal = ecalAssoTrack.begin();
775 itecal != ecalAssoTrack.end(); ++itecal) {
776 linked_e=linked_e+elements[itecal->second].clusterRef()->energy();
779 if(!hcalAssoTrack.empty()) {
780 for(std::multimap<double, unsigned int>::iterator ithcal = hcalAssoTrack.begin();
781 ithcal != hcalAssoTrack.end(); ++ithcal) {
782 linked_h=linked_h+elements[ithcal->second].clusterRef()->energy();
785 EoverPt=linked_e/elements[track_index].trackRef()->pt();
786 HoverPt=linked_h/elements[track_index].trackRef()->pt();
787 GlobalVector rvtx(elements[track_index].trackRef()->innerPosition().
X()-primaryvtx.
x(),
788 elements[track_index].trackRef()->innerPosition().Y()-primaryvtx.
y(),
789 elements[track_index].trackRef()->innerPosition().Z()-primaryvtx.
z());
790 double vtx_phi=rvtx.
phi();
792 del_phi=fabs(
deltaPhi(vtx_phi, elements[track_index].trackRef()->innerMomentum().
Phi()));
803 switch( pfbe.
type() ) {
807 std::multimap<double,unsigned> tks;
813 for(
const auto& tk : tks ) {
832 <<
"Resetting PFEGammaAlgo for new block and running!" << std::endl;
842 LOGVERB(
"PFEGammaAlgo") <<
"Splaying block" << std::endl;
845 if(
isAMuon(pfelement) )
continue;
846 const size_t itype = (size_t)pfelement.type();
848 _splayedblock[itype].push_back(std::make_pair(&pfelement,
true));
853 std::stringstream splayout;
854 for(
size_t itype = 0; itype <
_splayedblock.size(); ++itype ) {
855 splayout <<
"\tType: " << itype <<
" indices: ";
857 splayout << flaggedelement.first->index() <<
' ';
859 if( itype !=
_splayedblock.size() - 1 ) splayout << std::endl;
861 LOGVERB(
"PFEGammaAlgo") << splayout.str();
898 <<
"Dumping after GSF and KF Track (Primary) Linking : " << std::endl;
905 <<
"Dumping after first merging operation : " << std::endl;
911 for(
auto& RO : _refinableObjects ) {
922 <<
"Dumping after ECAL to Track (Secondary) Linking : " << std::endl;
929 <<
"There are " << _refinableObjects.size()
930 <<
" after the 2nd merging step." << std::endl;
934 for(
auto& RO : _refinableObjects ) {
941 std::sort(RO.ecalclusters.begin(), RO.ecalclusters.end(),
944 {
return ( a.first->clusterRef()->correctedEnergy() >
945 b.first->clusterRef()->correctedEnergy() ) ; });
946 setROElectronCluster(RO);
950 <<
"There are " << _refinableObjects.size()
951 <<
" after the unlinking and vetos step." << std::endl;
966 <<
"creating SC-based proto-object" << std::endl
967 <<
"\tSC at index: " << element.first->index()
968 <<
" has type: " << element.first->type() << std::endl;
969 element.second =
false;
1000 std::list<ProtoEGObject>::iterator objsbegin, objsend;
1003 <<
"creating GSF-based proto-object" << std::endl
1004 <<
"\tGSF at index: " << element.first->index()
1005 <<
" has type: " << element.first->type() << std::endl;
1011 element.second =
false;
1026 std::stringstream gsf_err;
1027 elementAsGSF->
Dump(gsf_err,
"\t");
1029 <<
"Found a GSF track with no seed! This should not happen!" 1030 << std::endl << gsf_err.str() << std::endl;
1034 element.second =
false;
1036 fromGSF.
primaryGSFs.push_back(std::make_pair(elementAsGSF,
true));
1040 brem.first->index(),
1043 if( dist == 0.001
f ) {
1046 fromGSF.
brems.push_back(std::make_pair(eAsBrem,
true));
1049 brem.second =
false;
1059 <<
"GSF-based proto-object is ECAL driven, merging SC-cand" 1066 SeedMatchesToProtoObject sctoseedmatch(fromGSF.
electronSeed);
1070 auto clusmatch = std::find_if(objsbegin,objsend,sctoseedmatch);
1071 if( clusmatch != objsend ) {
1072 fromGSF.
parentSC = clusmatch->parentSC;
1082 <<
"Encountered the known GSF-SC splitting bug " 1083 <<
" in PFBlockAlgo! We should really fix this!" << std::endl;
1085 std::stringstream gsf_err;
1086 elementAsGSF->
Dump(gsf_err,
"\t");
1088 <<
"Expected SuperCluster from ECAL driven GSF seed " 1089 <<
"was not found in the block!" << std::endl
1090 << gsf_err.str() << std::endl;
1114 std::vector<PFClusterFlaggedElement>& ecalclusters,
1116 ecalclusters.clear();
1119 <<
"Pointer to SC element: 0x" 1120 << std::hex << thesc <<
std::dec << std::endl
1121 <<
"cleared ecalclusters and ecal2ps!" << std::endl;
1126 if( ecalbegin == ecalend && hgcalbegin == hgcalend ) {
1127 LOGERR(
"PFEGammaAlgo::unwrapSuperCluster()")
1128 <<
"There are no ECAL elements in a block with imported SC!" 1129 <<
" This is a bug we should fix this!" 1137 <<
"SuperCluster pointed to by block element is null!" 1141 <<
"Got a valid super cluster ref! 0x" 1142 << std::hex << scref.
get() <<
std::dec << std::endl;
1143 const size_t nscclusters = scref->clustersSize();
1144 const size_t nscpsclusters = scref->preshowerClustersSize();
1145 size_t npfpsclusters = 0;
1146 size_t npfclusters = 0;
1148 <<
"Precalculated cluster multiplicities: " 1149 << nscclusters <<
' ' << nscpsclusters << std::endl;
1150 NotCloserToOther<reco::PFBlockElement::SC,reco::PFBlockElement::ECAL>
1152 NotCloserToOther<reco::PFBlockElement::SC,reco::PFBlockElement::HGCAL>
1154 auto ecalfirstnotinsc = std::partition(ecalbegin,ecalend,ecalClustersInSC);
1155 auto hgcalfirstnotinsc = std::partition(hgcalbegin,hgcalend,hgcalClustersInSC);
1167 if( ecalfirstnotinsc == ecalbegin &&
1168 hgcalfirstnotinsc == hgcalbegin) {
1169 LOGERR(
"PFEGammaAlgo::unwrapSuperCluster()")
1170 <<
"No associated block elements to SuperCluster!" 1171 <<
" This is a bug we should fix!" 1178 if( is_pf_sc && nscclusters != npfclusters ) {
1179 std::stringstream sc_err;
1180 thesc->
Dump(sc_err,
"\t");
1182 <<
"The number of found ecal elements (" 1183 << nscclusters <<
") in block is not the same as" 1184 <<
" the number of ecal PF clusters reported by the PFSuperCluster" 1185 <<
" itself (" << npfclusters
1186 <<
")! This should not happen!" << std::endl
1187 << sc_err.str() << std::endl;
1189 for(
auto ecalitr = ecalbegin; ecalitr != ecalfirstnotinsc; ++ecalitr ) {
1195 if(!is_pf_sc &&
std::find(safePFClusters.begin(),safePFClusters.end(),elemascluster) ==
1196 safePFClusters.end() )
continue;
1199 ecalclusters.push_back(std::make_pair(elemascluster,
true));
1201 ecalitr->second =
false;
1205 auto emplaceresult = ecal2ps.emplace(elemascluster,
1206 ClusterMap::mapped_type());
1207 if( !emplaceresult.second ) {
1208 std::stringstream clus_err;
1209 elemascluster->
Dump(clus_err,
"\t");
1211 <<
"List of pointers to ECAL block elements contains non-unique items!" 1212 <<
" This is very bad!" << std::endl
1213 <<
"cluster ptr = 0x" << std::hex << elemascluster <<
std::dec 1214 << std::endl << clus_err.str() << std::endl;
1216 ClusterMap::mapped_type& eslist = emplaceresult.first->second;
1220 for(
auto hgcalitr = hgcalbegin; hgcalitr != hgcalfirstnotinsc; ++hgcalitr ) {
1226 if(!is_pf_sc &&
std::find(safePFClusters.begin(),safePFClusters.end(),elemascluster) ==
1227 safePFClusters.end() )
continue;
1230 ecalclusters.push_back(std::make_pair(elemascluster,
true));
1232 hgcalitr->second =
false;
1250 <<
" Unwrapped SC has " << npfclusters <<
" ECAL sub-clusters" 1251 <<
" and " << npfpsclusters <<
" PreShower layers 1 & 2 clusters!" 1259 ClusterMap::mapped_type& eslist) {
1262 EEtoPSElement ecalkey = std::make_pair(clusptr.
key(),clusptr);
1263 auto assc_ps = std::equal_range(
eetops_->cbegin(),
1269 for(
auto pscl = assc_ps.first; pscl != assc_ps.second; ++pscl ) {
1270 if( pscl->second == temp ) {
1271 const ClusterElement* pstemp =
1272 docast(
const ClusterElement*,ps1.first);
1279 for(
auto pscl = assc_ps.first; pscl != assc_ps.second; ++pscl ) {
1280 if( pscl->second == temp ) {
1281 const ClusterElement* pstemp =
1282 docast(
const ClusterElement*,ps2.first);
1287 return eslist.size();
1295 <<
" refinable objects for this block: " << std::endl;
1297 std::stringstream
info;
1298 info <<
"Refinable Object:" << std::endl;
1300 info <<
"\tSuperCluster element attached to object:" << std::endl
1302 ro.parentSC->Dump(info,
"\t");
1305 if( ro.electronSeed.isNonnull() ) {
1306 info <<
"\tGSF element attached to object:" << std::endl;
1307 ro.primaryGSFs.front().first->Dump(info,
"\t");
1309 info <<
"firstBrem : " << ro.firstBrem
1310 <<
" lateBrem : " << ro.lateBrem
1311 <<
" nBrems with cluster : " << ro.nBremsWithClusters
1313 if( ro.electronClusters.size() && ro.electronClusters[0] ) {
1314 info <<
"electron cluster : ";
1315 ro.electronClusters[0]->Dump(info,
"\t");
1318 info <<
" no electron cluster." << std::endl;
1321 if( ro.primaryKFs.size() ) {
1322 info <<
"\tPrimary KF tracks attached to object: " << std::endl;
1323 for(
const auto& kf : ro.primaryKFs ) {
1324 kf.first->Dump(info,
"\t");
1328 if( ro.secondaryKFs.size() ) {
1329 info <<
"\tSecondary KF tracks attached to object: " << std::endl;
1330 for(
const auto& kf : ro.secondaryKFs ) {
1331 kf.first->Dump(info,
"\t");
1335 if( ro.brems.size() ) {
1336 info <<
"\tBrem tangents attached to object: " << std::endl;
1337 for(
const auto& brem : ro.brems ) {
1338 brem.first->Dump(info,
"\t");
1342 if( ro.ecalclusters.size() ) {
1343 info <<
"\tECAL clusters attached to object: " << std::endl;
1344 for(
const auto& clus : ro.ecalclusters ) {
1345 clus.first->Dump(info,
"\t");
1347 if( ro.ecal2ps.find(clus.first) != ro.ecal2ps.end() ) {
1348 for(
const auto& psclus : ro.ecal2ps.at(clus.first) ) {
1349 info <<
"\t\t Attached PS Cluster: ";
1350 psclus.first->Dump(info,
"");
1364 typedef std::multimap<double, unsigned> MatchedMap;
1368 MatchedMap matchedGSFs, matchedECALs;
1369 std::unordered_map<GsfTrackElementPtr,MatchedMap> gsf_ecal_cache;
1371 matchedGSFs.clear();
1376 if( matchedGSFs.empty() ) {
1381 std::partial_sort(ecalbegin,ecalbegin+1,ecalend,closestTrackToECAL);
1384 const float dist =
_currentblock->dist(kftrack.first->index(),
1385 closestECAL.first->index(),
1391 closestECAL.first->index(),
1394 if( dist_sc != -1.0
f) { inSC =
true;
break; }
1397 if( dist != -1.0
f && closestECAL.second ) {
1398 bool gsflinked =
false;
1400 for(
const auto& gsfflag :
_splayedblock[reco::PFBlockElement::GSF]) {
1407 if( !gsf_ecal_cache.count(elemasgsf) ) {
1408 matchedECALs.clear();
1413 gsf_ecal_cache.emplace(elemasgsf,matchedECALs);
1414 MatchedMap().swap(matchedECALs);
1416 const MatchedMap& ecal_matches = gsf_ecal_cache[elemasgsf];
1417 if( !ecal_matches.empty() ) {
1418 if( ecal_matches.begin()->second == closestECAL.first->index() ) {
1424 if( !gsflinked && !inSC) {
1431 trackref->hitPattern().numberOfLostHits(HitPattern::MISSING_INNER_HITS);
1432 bool fromprimaryvertex =
false;
1436 fromprimaryvertex =
true;
1442 closestECAL.second =
false;
1459 if( ROs.size() < 2 )
return;
1460 bool check_for_merge =
true;
1461 while( check_for_merge ) {
1466 for(
auto it1 = ROs.begin(); it1 != ROs.end(); ++it1 ) {
1467 TestIfROMergableByLink mergeTest(*it1);
1468 auto find_start = it1; ++find_start;
1469 auto has_merge = std::find_if(find_start,ROs.end(),mergeTest);
1470 if( has_merge != ROs.end() && it1 != ROs.begin() ) {
1476 TestIfROMergableByLink mergeTest(thefront);
1477 auto mergestart = ROs.begin(); ++mergestart;
1478 auto nomerge = std::partition(mergestart,ROs.end(),mergeTest);
1479 if( nomerge != mergestart ) {
1480 LOGDRESSED(
"PFEGammaAlgo::mergeROsByAnyLink()")
1482 <<
" to merge by links to the front!" << std::endl;
1483 for(
auto roToMerge = mergestart; roToMerge != nomerge; ++roToMerge) {
1486 if( !thefront.
ecalclusters.empty() && !roToMerge->ecalclusters.empty() ) {
1487 if( thefront.
ecalclusters.front().first->clusterRef()->layer() !=
1488 roToMerge->ecalclusters.front().first->clusterRef()->layer() ) {
1489 LOGWARN(
"PFEGammaAlgo::mergeROsByAnyLink")
1490 <<
"Tried to merge EB and EE clusters! Skipping!";
1491 ROs.push_back(*roToMerge);
1497 roToMerge->ecalclusters.begin(),
1498 roToMerge->ecalclusters.end());
1499 thefront.
ecal2ps.insert(roToMerge->ecal2ps.begin(),
1500 roToMerge->ecal2ps.end());
1502 roToMerge->secondaryKFs.begin(),
1503 roToMerge->secondaryKFs.end());
1506 roToMerge->localMap.begin(),
1507 roToMerge->localMap.end());
1509 if( !thefront.
parentSC && roToMerge->parentSC ) {
1510 thefront.
parentSC = roToMerge->parentSC;
1513 roToMerge->electronSeed.isNonnull() ) {
1516 roToMerge->primaryGSFs.begin(),
1517 roToMerge->primaryGSFs.end());
1519 roToMerge->primaryKFs.begin(),
1520 roToMerge->primaryKFs.end());
1522 roToMerge->brems.begin(),
1523 roToMerge->brems.end());
1526 thefront.
firstBrem = roToMerge->firstBrem;
1527 thefront.
lateBrem = roToMerge->lateBrem;
1529 roToMerge->electronSeed.isNonnull()) {
1530 LOGWARN(
"PFEGammaAlgo::mergeROsByAnyLink")
1531 <<
"Need to implement proper merging of two gsf candidates!" 1535 ROs.erase(mergestart,nomerge);
1537 ROs.push_back(ROs.front());
1540 check_for_merge =
false;
1543 LOGDRESSED(
"PFEGammaAlgo::mergeROsByAnyLink()")
1544 <<
"After merging by links there are: " << ROs.size()
1545 <<
" refinable EGamma objects!" << std::endl;
1563 NotCloserToOther<reco::PFBlockElement::GSF,reco::PFBlockElement::TRACK>
1566 auto notlinked = std::partition(KFbegin,KFend,gsfTrackToKFs);
1568 for(
auto kft = KFbegin; kft != notlinked; ++kft ) {
1575 kft->second =
false;
1576 RO.
primaryKFs.push_back(std::make_pair(elemaskf,
true));
1579 }
else if ( elemaskf->
trackType(convType) ) {
1580 kft->second =
false;
1581 RO.
secondaryKFs.push_back(std::make_pair(elemaskf,
true));
1600 throw cms::Exception(
"PFEGammaAlgo::linkRefinableObjectPrimaryKFsToSecondaryKFs()")
1601 <<
"A KF track from conversion has been assigned as a primary!!" 1604 NotCloserToOther<reco::PFBlockElement::TRACK,reco::PFBlockElement::TRACK,true>
1607 auto notlinked = std::partition(KFbegin,KFend,kfTrackToKFs);
1609 for(
auto kft = KFbegin; kft != notlinked; ++kft ) {
1615 kft->second =
false;
1616 RO.
secondaryKFs.push_back(std::make_pair(elemaskf,
true));
1634 NotCloserToOther<reco::PFBlockElement::GSF,reco::PFBlockElement::ECAL>
1636 CompatibleEoPOut eoverp_test(primgsf.first);
1638 auto notmatched_blk = std::partition(ECALbegin,ECALend,gsfTracksToECALs);
1639 notmatched_blk = std::partition(ECALbegin,notmatched_blk,eoverp_test);
1641 auto notmatched_sc = std::partition(RO.
ecalclusters.begin(),
1644 notmatched_sc = std::partition(RO.
ecalclusters.begin(),
1652 LOGDRESSED(
"PFEGammaAlgo::linkGSFTracktoECAL()")
1653 <<
"Found a cluster already in RO by GSF extrapolation" 1654 <<
" at ECAL surface!" << std::endl
1655 << *elemascluster << std::endl;
1661 for(
auto ecal = ECALbegin;
ecal != notmatched_blk; ++
ecal ) {
1664 LOGDRESSED(
"PFEGammaAlgo::linkGSFTracktoECAL()")
1665 <<
"Found a cluster not already in RO by GSF extrapolation" 1666 <<
" at ECAL surface!" << std::endl
1667 << *elemascluster << std::endl;
1668 if( addPFClusterToROSafe(elemascluster,RO) ) {
1672 ecal->second =
false;
1685 NotCloserToOther<reco::PFBlockElement::GSF,reco::PFBlockElement::HCAL>
1687 CompatibleEoPOut eoverp_test(primgsf.first);
1688 auto notmatched = std::partition(HCALbegin,HCALend,gsfTracksToHCALs);
1689 for(
auto hcal = HCALbegin;
hcal != notmatched; ++
hcal ) {
1693 LOGDRESSED(
"PFEGammaAlgo::linkGSFTracktoECAL()")
1694 <<
"Found an HCAL cluster associated to GSF extrapolation" 1699 hcal->second =
false;
1715 std::vector<PFClusterFlaggedElement>& currentECAL = RO.
ecalclusters;
1718 NotCloserToOther<reco::PFBlockElement::TRACK,reco::PFBlockElement::ECAL>
1720 NotCloserToOther<reco::PFBlockElement::GSF,reco::PFBlockElement::ECAL>
1723 auto notmatched_sc = std::partition(currentECAL.begin(),
1727 notmatched_sc = std::partition(currentECAL.begin(),
1730 for(
auto ecalitr = currentECAL.begin(); ecalitr != notmatched_sc;
1736 LOGDRESSED(
"PFEGammaAlgo::linkKFTracktoECAL()")
1737 <<
"Found a cluster already in RO by KF extrapolation" 1738 <<
" at ECAL surface!" << std::endl
1739 << *elemascluster << std::endl;
1746 auto notmatched_blk = std::partition(ECALbegin,ECALend,kfTrackToECALs);
1748 notmatched_blk = std::partition(ECALbegin,notmatched_blk,kfTrackGSFToECALs);
1749 for(
auto ecalitr = ECALbegin; ecalitr != notmatched_blk; ++ecalitr ) {
1752 if( addPFClusterToROSafe(elemascluster,RO) ) {
1754 ecalitr->second =
false;
1756 LOGDRESSED(
"PFEGammaAlgo::linkKFTracktoECAL()")
1757 <<
"Found a cluster not in RO by KF extrapolation" 1758 <<
" at ECAL surface!" << std::endl
1759 << *elemascluster << std::endl;
1770 if( RO.
brems.empty() )
return;
1773 int lastBremTrajPos = -1;
1774 for(
auto& bremflagged : RO.
brems ) {
1775 bool has_clusters =
false;
1776 TrajPos = (bremflagged.first->indTrajPoint())-2;
1779 NotCloserToOther<reco::PFBlockElement::BREM,reco::PFBlockElement::ECAL>
1784 auto notmatched_rsc = std::partition(RSCBegin,RSCEnd,BremToECALs);
1785 for(
auto ecal = RSCBegin;
ecal != notmatched_rsc; ++
ecal ) {
1787 std::abs(
ecal->first->clusterRef()->positionREP().eta() -
1788 bremflagged.first->positionAtECALEntrance().eta() );
1789 if( deta < 0.015 ) {
1790 has_clusters =
true;
1791 if( lastBremTrajPos == -1 || lastBremTrajPos < TrajPos ) {
1792 lastBremTrajPos = TrajPos;
1794 if( FirstBrem == -1 || TrajPos < FirstBrem ) {
1795 FirstBrem = TrajPos;
1799 <<
"Found a cluster already in SC linked to brem extrapolation" 1800 <<
" at ECAL surface!" << std::endl;
1806 auto notmatched_block = std::partition(ECALbegin,ECALend,BremToECALs);
1807 for(
auto ecal = ECALbegin;
ecal != notmatched_block; ++
ecal ) {
1809 std::abs(
ecal->first->clusterRef()->positionREP().eta() -
1810 bremflagged.first->positionAtECALEntrance().eta() );
1811 if( deta < 0.015 ) {
1812 has_clusters =
true;
1813 if( lastBremTrajPos == -1 || lastBremTrajPos < TrajPos ) {
1814 lastBremTrajPos = TrajPos;
1816 if( FirstBrem == -1 || TrajPos < FirstBrem ) {
1818 FirstBrem = TrajPos;
1823 if( addPFClusterToROSafe(elemasclus,RO) ) {
1828 ecal->second =
false;
1830 <<
"Found a cluster not already associated by brem extrapolation" 1831 <<
" at ECAL surface!" << std::endl;
1845 IsConversionTrack<reco::PFBlockElementTrack> isConvKf;
1850 auto ronotconv = std::partition(BeginROskfs,EndROskfs,isConvKf);
1852 for(
size_t idx = 0;
idx < convkfs_end; ++
idx ) {
1853 const std::vector<PFKFFlaggedElement>& secKFs = RO.
secondaryKFs;
1858 auto notmatched = std::partition(KFbegin,KFend,TracksToTracks);
1859 notmatched = std::partition(KFbegin,notmatched,isConvKf);
1860 for(
auto kf = KFbegin; kf != notmatched; ++kf ) {
1863 RO.
secondaryKFs.push_back( std::make_pair(elemaskf,
true) );
1874 IsConversionTrack<reco::PFBlockElementTrack> isConvKf;
1882 auto notmatchedkf = std::partition(KFbegin,KFend,ECALToTracks);
1883 auto notconvkf = std::partition(KFbegin,notmatchedkf,isConvKf);
1885 for(
auto kf = KFbegin; kf != notconvkf; ++kf ) {
1888 RO.
secondaryKFs.push_back( std::make_pair(elemaskf,
true) );
1894 for(
auto kf = notconvkf; kf != notmatchedkf; ++kf ) {
1897 kf->first->
index());
1901 RO.
secondaryKFs.push_back( std::make_pair(elemaskf,
true) );
1921 auto notmatched = std::partition(ECALbegin,ECALend,TracksToECALwithCut);
1922 for(
auto ecal = ECALbegin;
ecal != notmatched; ++
ecal ) {
1925 if( addPFClusterToROSafe(elemascluster,RO) ) {
1929 ecal->second =
false;
1937 const std::list<PFEGammaAlgo::ProtoEGObject>& ROs,
1944 egcands.reserve(ROs.size());
1945 egxs.reserve(ROs.size());
1947 for(
auto& RO : ROs ) {
1948 if( RO.ecalclusters.empty() &&
1953 if( !RO.primaryGSFs.empty() || !RO.primaryKFs.empty() ) {
1958 if( !RO.primaryKFs.empty() ) {
1959 cand.
setCharge(RO.primaryKFs[0].first->trackRef()->charge());
1961 cand.
setTrackRef(RO.primaryKFs[0].first->trackRef());
1964 if( !RO.primaryGSFs.empty() ) {
1965 cand.
setCharge(RO.primaryGSFs[0].first->GsftrackRef()->chargeMode());
1978 for(
const auto& bremflagged : RO.brems ) {
1983 for(
const auto&
ecal : RO.ecalclusters ) {
1986 if( RO.ecal2ps.count(clus) ) {
1987 for(
auto& ps : RO.ecal2ps.at(clus) ) {
1994 for(
const auto& secdkf : RO.secondaryKFs ) {
1998 bool no_conv_ref =
true;
1999 for(
const auto& convref : convrefs ) {
2000 if( convref.isNonnull() && convref.isAvailable() ) {
2002 no_conv_ref =
false;
2009 const auto &mvavalmapped = RO.singleLegConversionMvaMap.find(kf);
2012 float mvaval = ( mvavalmapped != RO.singleLegConversionMvaMap.end() ?
2013 mvavalmapped->second :
2026 float trkTime = 0, trkTimeErr = -1;
2027 if (!RO.primaryGSFs.empty() && RO.primaryGSFs[0].first->isTimeValid()) {
2028 trkTime = RO.primaryGSFs[0].first->time();
2029 trkTimeErr = RO.primaryGSFs[0].first->timeError();
2030 }
else if (!RO.primaryKFs.empty() && RO.primaryKFs[0].first->isTimeValid()) {
2031 trkTime = RO.primaryKFs[0].first->time();
2032 trkTimeErr = RO.primaryKFs[0].first->timeError();
2034 if (trkTimeErr >= 0) {
2035 cand.
setTime( trkTime, trkTimeErr );
2043 const double scE = the_sc.
energy();
2047 egDir = egDir.Unit();
2056 !RO.primaryGSFs.empty() ) {
2060 gref->pzMode(),gref->pMode());
2064 !RO.primaryKFs.empty() ) {
2074 xtra.
setMVA(ele_mva_value);
2076 egcands.push_back(cand);
2077 egxs.push_back(xtra);
2092 const double Ein_gsf = std::hypot(RefGSF->pMode(),m_el);
2093 double deta_gsfecal = 1e6;
2095 const double Ene_hcalgsf = std::accumulate(RO.
hcalClusters.begin(),
2100 {
return a +
b.first->clusterRef()->energy(); }
2103 RefKF = RO.
primaryKFs.front().first->trackRef();
2105 const double Eout_gsf = gsfElement->
Pout().t();
2107 double FirstEcalGsfEnergy(0.0), OtherEcalGsfEnergy(0.0), EcalBremEnergy(0.0);
2109 std::vector<const reco::PFCluster*> gsfcluster;
2111 const double cenergy =
ecal.first->clusterRef()->correctedEnergy();
2120 bool hasbrem =
false;
2121 for(
const auto& brem : RO.
brems ) {
2129 EcalBremEnergy += cenergy;
2132 if( hasgsf ) OtherEcalGsfEnergy += cenergy;
2133 if( haskf ) EcalBremEnergy += cenergy;
2134 if( !(hasgsf || haskf) ) OtherEcalGsfEnergy += cenergy;
2141 FirstEcalGsfEnergy = cref->correctedEnergy();
2142 deta_gsfecal = cref->positionREP().eta() - Etaout_gsf;
2143 gsfcluster.push_back(&*cref);
2159 if( FirstEcalGsfEnergy > 0.0 ) {
2163 const float Pt_gsf = RefGSF->ptMode();
2167 const double ptModeErrorGsf = RefGSF->ptModeError();
2168 dPtOverPt_gsf = (ptModeErrorGsf > 0. ? ptModeErrorGsf/Pt_gsf : 1.0);
2169 nhit_gsf = RefGSF->hitPattern().trackerLayersWithMeasurement();
2170 chi2_gsf = RefGSF->normalizedChi2();
2177 nhit_kf = RefKF->hitPattern().trackerLayersWithMeasurement();
2178 chi2_kf = RefKF->normalizedChi2();
2183 const double EcalETot =
2184 (FirstEcalGsfEnergy+OtherEcalGsfEnergy+EcalBremEnergy);
2188 (Ein_gsf - Eout_gsf) );
2194 HOverHE = Ene_hcalgsf/(Ene_hcalgsf + FirstEcalGsfEnergy);
2245 return hoc->
gbrEle_->GetAdaBoostClassifier(vars);
2255 IsConversionTrack<reco::PFBlockElementTrack> isConvKf;
2263 auto notmatchedkf = std::partition(KFbegin,KFend,ECALToTracks);
2264 auto notconvkf = std::partition(KFbegin,notmatchedkf,isConvKf);
2266 for(
auto kf = notconvkf; kf != notmatchedkf; ++kf ) {
2289 std::vector<const reco::PFCluster*> bare_ptrs;
2292 rawSCEnergy(0), corrSCEnergy(0), corrPSEnergy(0),
2293 PS1_clus_sum(0), PS2_clus_sum(0),
2294 ePS1(0), ePS2(0), ps1_energy(0.0), ps2_energy(0.0);
2295 int condP1(1), condP2(1);
2301 edm::refToPtr<reco::PFClusterCollection>(clus.first->clusterRef());
2302 bare_ptrs.push_back(clusptr.
get());
2304 const double cluseraw = clusptr->
energy();
2307 posX += cluseraw * cluspos.X();
2308 posY += cluseraw * cluspos.Y();
2309 posZ += cluseraw * cluspos.Z();
2311 if( isEE && RO.
ecal2ps.count(clus.first)) {
2314 condP1 = condP2 = 1;
2316 const auto& psclusters = RO.
ecal2ps.at(clus.first);
2318 for(
auto i_ps = psclusters.begin(); i_ps != psclusters.end(); ++i_ps) {
2319 const PFClusterRef& psclus = i_ps->first->clusterRef();
2321 auto const& recH_Frac = psclus->recHitFractions();
2323 switch( psclus->layer() ) {
2325 for (
auto const& recH : recH_Frac){
2326 ESDetId strip1 = recH.recHitRef()->detId();
2331 if(status_p1->getStatusCode() == 0) condP1 = 0;
2336 for (
auto const& recH : recH_Frac){
2337 ESDetId strip2 = recH.recHitRef()->detId();
2340 if(status_p2->getStatusCode() == 0) condP2 = 0;
2350 PS1_clus_sum = std::accumulate(psclusters.begin(),psclusters.end(),
2352 PS2_clus_sum = std::accumulate(psclusters.begin(),psclusters.end(),
2355 if(condP1 == 1) ePS1 = -1.;
2356 if(condP2 == 1) ePS2 = -1.;
2360 PS1_clus_sum,PS2_clus_sum,
2364 if(ePS1 == -1.) ePS1 = 0;
2365 if(ePS2 == -1.) ePS2 = 0;
2367 rawSCEnergy += cluseraw;
2368 corrSCEnergy += cluscalibe;
2371 corrPSEnergy += ePS1 + ePS2;
2373 posX /= rawSCEnergy;
2374 posY /= rawSCEnergy;
2375 posZ /= rawSCEnergy;
2381 edm::refToPtr<reco::PFClusterCollection>(RO.
ecalclusters.front().
2382 first->clusterRef());
2390 edm::refToPtr<reco::PFClusterCollection>(clus.first->clusterRef());
2393 for(
auto& hit_and_fraction : hits_and_fractions ) {
2397 if( RO.
ecal2ps.count(clus.first) ) {
2398 const auto& cluspsassociation = RO.
ecal2ps.at(clus.first);
2402 for(
const auto& pscluselem : cluspsassociation ) {
2404 edm::refToPtr<reco::PFClusterCollection>(pscluselem.first->
2415 throw cms::Exception(
"PFECALSuperClusterAlgo::buildSuperCluster")
2416 <<
"Found a PS cluster matched to more than one EE cluster!" 2417 << std::endl << std::hex << psclus.
get() <<
" == " 2418 << found_pscluster->get() <<
std::dec << std::endl;
2441 const double Pin_gsf = RO.
primaryGSFs.front().first->GsftrackRef()->pMode();
2442 const double gsfOuterEta =
2443 RO.
primaryGSFs.front().first->positionAtECALEntrance().Eta();
2444 double tot_ecal= 0.0;
2445 std::vector<double> min_brem_dists;
2446 std::vector<double> closest_brem_eta;
2449 tot_ecal +=
ecal.first->clusterRef()->correctedEnergy();
2452 double min_brem_dist = 5000.0;
2453 double eta = -999.0;
2454 for(
const auto& brem : RO.
brems ) {
2456 ecal.first->index(),
2459 if( dist < min_brem_dist && dist != -1.0
f ) {
2460 min_brem_dist = dist;
2461 eta = brem.first->positionAtECALEntrance().Eta();
2464 min_brem_dists.push_back(min_brem_dist);
2465 closest_brem_eta.push_back(eta);
2473 const float secpin = secd_kf->first->trackRef()->p();
2474 bool remove_this_kf =
false;
2478 const float minbremdist = min_brem_dists[bremidx];
2479 const double ecalenergy =
ecal->first->clusterRef()->correctedEnergy();
2480 const double Epin = ecalenergy/secpin;
2481 const double detaGsf =
2482 std::abs(gsfOuterEta -
ecal->first->clusterRef()->positionREP().Eta());
2483 const double detaBrem =
2484 std::abs(closest_brem_eta[bremidx] -
2485 ecal->first->clusterRef()->positionREP().Eta());
2492 const float tkdist =
_currentblock->dist(secd_kf->first->index(),
2493 ecal->first->index(),
2500 if( Epin > 3 && kf_matched != RO.
localMap.end() &&
2501 tkdist != -1.0f && tkdist < minbremdist &&
2502 detaGsf > 0.05 && detaBrem > 0.015) {
2503 double res_with =
std::abs((tot_ecal-Pin_gsf)/Pin_gsf);
2504 double res_without =
std::abs((tot_ecal-ecalenergy-Pin_gsf)/Pin_gsf);
2505 if(res_without < res_with) {
2507 <<
" REJECTED_RES totenergy " << tot_ecal
2508 <<
" Pin_gsf " << Pin_gsf
2509 <<
" cluster to secondary " << ecalenergy
2510 <<
" res_with " << res_with
2511 <<
" res_without " << res_without << std::endl;
2512 tot_ecal -= ecalenergy;
2513 remove_this_kf =
true;
2519 if( remove_this_kf ) {
2528 bool removeFreeECAL,
2529 bool removeSCEcal) {
2530 std::vector<bool> cluster_in_sc;
2537 bool remove_this_kf =
false;
2538 NotCloserToOther<reco::PFBlockElement::TRACK,reco::PFBlockElement::HCAL>
2543 const float secpin = trkRef->p();
2545 for(
auto ecal = ecal_begin;
ecal != ecal_end; ++
ecal ) {
2546 const double ecalenergy =
ecal->first->clusterRef()->correctedEnergy();
2549 if( cluster_in_sc.size() < clus_idx + 1) {
2553 ecal->first->index(),
2557 cluster_in_sc.push_back(dist != -1.0
f);
2568 if( kf_matched != RO.
localMap.end() ) {
2569 auto hcal_matched = std::partition(hcal_begin,hcal_end,tracksToHCALs);
2570 for(
auto hcalclus = hcal_begin;
2571 hcalclus != hcal_matched;
2575 const double hcalenergy = clusthcal->
clusterRef()->energy();
2576 const double hpluse = ecalenergy+hcalenergy;
2577 const bool isHoHE = ( (hcalenergy / hpluse ) > 0.1 && goodTrack );
2578 const bool isHoE = ( hcalenergy > ecalenergy );
2579 const bool isPoHE = ( secpin > hpluse );
2580 if( cluster_in_sc[clus_idx] ) {
2581 if(isHoE || isPoHE) {
2583 <<
"REJECTED TRACK FOR H/E or P/(H+E), CLUSTER IN SC" 2584 <<
" H/H+E " << (hcalenergy / hpluse)
2585 <<
" H/E " << (hcalenergy > ecalenergy)
2586 <<
" P/(H+E) " << (secpin/hpluse)
2587 <<
" HCAL ENE " << hcalenergy
2588 <<
" ECAL ENE " << ecalenergy
2589 <<
" secPIN " << secpin
2590 <<
" Algo Track " << trkRef->algo() << std::endl;
2591 remove_this_kf =
true;
2596 <<
"REJECTED TRACK FOR H/H+E, CLUSTER NOT IN SC" 2597 <<
" H/H+E " << (hcalenergy / hpluse)
2598 <<
" H/E " << (hcalenergy > ecalenergy)
2599 <<
" P/(H+E) " << (secpin/hpluse)
2600 <<
" HCAL ENE " << hcalenergy
2601 <<
" ECAL ENE " << ecalenergy
2602 <<
" secPIN " << secpin
2603 <<
" Algo Track " <<trkRef->algo() << std::endl;
2604 remove_this_kf =
true;
2610 if( remove_this_kf ) {
2621 bool isPrimary =
false;
2627 PFRecTrackRef kfPfRef_fromGsf = (*gsfPfRef).kfPFRecTrackRef();
2632 if(kfref == kfref_fromGsf)
float EtotBremPinPoutMode
const SuperClusterRef & superClusterRef() const
const math::XYZTLorentzVector & Pout() const
Abstract base class for a PFBlock element (track, cluster...)
const math::XYZPoint & position() const
cluster centroid position
CaloCluster_iterator preshowerClustersBegin() const
fist iterator over PreshowerCluster constituents
const reco::GsfTrackRef & GsftrackRef() const
std::vector< PFClusterFlaggedElement > ecalclusters
static bool overlap(const reco::CaloCluster &sc1, const reco::CaloCluster &sc, float minfrac=0.01, bool debug=false)
bool isNonnull() const
Checks for non-null.
void setSuperClusterRef(reco::SuperClusterRef sc)
set reference to the corresponding supercluster
Ptr< typename C::value_type > refToPtr(Ref< C, typename C::value_type, refhelper::FindUsingAdvance< C, typename C::value_type > > const &ref)
double correctedEnergy() const
reco::PFCandidateEGammaExtraCollection egExtra_
std::vector< std::pair< unsigned int, unsigned int > > fifthStepKfTrack_
reco::SuperClusterCollection refinedscs_
void addHitAndFraction(DetId id, float fraction)
reco::PFBlockRef parentBlock
void Dump(std::ostream &out=std::cout, const char *tab=" ") const override
print the object inside the element
void unlinkRefinableObjectKFandECALWithBadEoverP(ProtoEGObject &)
trackRef_iterator tracks_end() const
last iterator over tracks
static bool isMuon(const reco::PFBlockElement &elt)
void setPositionAtECALEntrance(const math::XYZPointF &pos)
set position at ECAL entrance
void setGsfElectronClusterRef(const reco::PFBlockRef &blk, const reco::PFBlockElementCluster &ref)
set gsf electron cluster ref
float calculate_ele_mva(const pfEGHelpers::HeavyObjectCache *hoc, const ProtoEGObject &, reco::PFCandidateEGammaExtra &)
const PFClusterRef & clusterRef() const override
void addSingleLegConvTrackRefMva(const std::pair< reco::TrackRef, float > &trackrefmva)
add Single Leg Conversion TrackRef
void setPreshowerEnergyPlane2(double preshowerEnergy2)
std::pair< const PFClusterElement *, bool > PFClusterFlaggedElement
const self & getMap() const
T const * get() const
Returns C++ pointer to the item.
double y() const
y coordinate
void setHadEnergy(float val)
set the had energy. The cluster energies should be entered before
const math::XYZPointF & positionAtECALEntrance() const
std::shared_ptr< PFEnergyCalibration > thePFEnergyCalibration
const reco::TrackRef & trackRef() const override
void Dump(std::ostream &out=std::cout, const char *tab=" ") const override
print the object inside the element
const ConversionRefVector & convRefs() const override
std::map< unsigned int, Link > LinkData
Geom::Phi< T > phi() const
double pflowPhiWidth() const
std::vector< PFClusterFlaggedElement > hcalClusters
bool isPrimaryTrack(const reco::PFBlockElementTrack &KfEl, const reco::PFBlockElementGsfTrack &GsfEl)
bool trackType(TrackType trType) const override
void linkRefinableObjectPrimaryGSFTrackToECAL(ProtoEGObject &)
const GsfPFRecTrackRef & GsftrackRefPF() const
const edm::OwnVector< reco::PFBlockElement > & elements() const
const std::vector< std::pair< DetId, float > > & hitsAndFractions() const
edm::Ref< TrackExtraCollection > TrackExtraRef
persistent reference to a TrackExtra
void linkRefinableObjectECALToSingleLegConv(const pfEGHelpers::HeavyObjectCache *hoc, ProtoEGObject &)
std::vector< const PFClusterElement * > electronClusters
unsigned int index
index type
const LinkData & linkData() const
std::vector< std::vector< PFFlaggedElement > > _splayedblock
void setSeed(const CaloClusterPtr &r)
list of used xtals by DetId // now inherited by CaloCluster
const math::XYZTLorentzVector & Pin() const
std::pair< const PFGSFElement *, bool > PFGSFFlaggedElement
edm::Ptr< CaloCluster > CaloClusterPtr
void linkRefinableObjectBremTangentsToECAL(ProtoEGObject &)
ROOT::Math::PositionVector3D< ROOT::Math::Cartesian3D< float > > XYZPointF
point in space with cartesian internal representation
const reco::Vertex * primaryVtx
unsigned int indTrajPoint() const
void find(edm::Handle< EcalRecHitCollection > &hits, DetId thisDet, std::vector< EcalRecHitCollection::const_iterator > &hit, bool debug=false)
reco::PFBlockRef _currentblock
void setGsfTrackRef(const reco::GsfTrackRef &ref)
set gsftrack reference
std::pair< const reco::PFBlockElement *, bool > PFFlaggedElement
void setPhiWidth(double pw)
const Point & position() const
position
double pflowEtaWidth() const
std::pair< const PFSCElement *, bool > PFSCFlaggedElement
const math::XYZPointF & positionAtECALEntrance() const
std::unique_ptr< const GBRForest > gbrEle_
edm::Handle< reco::PFCluster::EEtoPSAssociation > eetops_
void setCharge(Charge q) final
set electric charge
XYZTLorentzVectorD XYZTLorentzVector
Lorentz vector with cylindrical internal representation using pseudorapidity.
void set_mva_e_pi(float mvaNI)
std::vector< PFKFFlaggedElement > secondaryKFs
void setEtaWidth(double ew)
void setSigmaEtaEta(float val)
set the sigmaetaeta
void dumpCurrentRefinableObjects() const
Container::value_type value_type
void initializeProtoCands(std::list< ProtoEGObject > &)
void linkRefinableObjectPrimaryKFsToSecondaryKFs(ProtoEGObject &)
bool unwrapSuperCluster(const reco::PFBlockElementSuperCluster *, std::vector< PFClusterFlaggedElement > &, ClusterMap &)
bool goodTrack(const reco::Track *pTrack, math::XYZPoint leadPV, trackSelectionParameters parameters, bool debug=false)
double pflowSigmaEtaEta() const
bool fromPFSuperCluster() const
std::unique_ptr< const GBRForest > gbrSingleLeg_
void setCorrectedEnergy(double cenergy)
void addElementInBlock(const reco::PFBlockRef &blockref, unsigned elementIndex)
add an element to the current PFCandidate
void swap(edm::DataFrameContainer &lhs, edm::DataFrameContainer &rhs)
reco::PFCluster::EEtoPSAssociation EEtoPSAssociation
PFEGammaAlgo(const PFEGConfigInfo &)
bool produceEGCandsWithNoSuperCluster
const PFSCElement * parentSC
bool trackType(TrackType trType) const override
std::vector< reco::PFCandidateEGammaExtra > PFCandidateEGammaExtraCollection
collection of PFCandidateEGammaExtras
const_iterator find(uint32_t rawId) const
std::vector< PFBremFlaggedElement > brems
void setEarlyBrem(float val)
set EarlyBrem
Abs< T >::type abs(const T &t)
double z() const
z coordinate
void setGsfTrackPout(const math::XYZTLorentzVector &pout)
set the pout (not trivial to get from the GSF track)
double energy() const
cluster energy
T const * get() const
Returns C++ pointer to the item.
std::list< ProtoEGObject > _refinableObjects
KFValMap singleLegConversionMvaMap
bool isNull() const
Checks for null.
void Dump(std::ostream &out=std::cout, const char *tab=" ") const override
print the object inside the element
reco::PFCandidateEGammaExtraCollection outcandsextra_
double energy() const
cluster energy
void linkKFTrackToECAL(const PFKFFlaggedElement &, ProtoEGObject &)
def elem(elemtype, innerHTML='', html_class='', kwargs)
void setEcalEnergy(float eeRaw, float eeCorr)
set corrected Ecal energy
reco::PFBlock::LinkData _currentlinks
void buildAndRefineEGObjects(const pfEGHelpers::HeavyObjectCache *hoc, const reco::PFBlockRef &block)
std::vector< reco::PFCandidate > PFCandidateCollection
collection of PFCandidates
double x() const
x coordinate
double rawEnergy() const
raw uncorrected energy (sum of energies of component BasicClusters)
float EvaluateSingleLegMVA(const pfEGHelpers::HeavyObjectCache *hoc, const reco::PFBlockRef &blockref, const reco::Vertex &primaryvtx, unsigned int track_index)
void fill_extra_info(const ProtoEGObject &, reco::PFCandidateEGammaExtra &)
reco::PFCandidateCollection egCandidate_
bool applyCrackCorrections
bool isAMuon(const reco::PFBlockElement &)
void setDeltaEta(float val)
set the delta eta
void setGsfTrackRef(const reco::GsfTrackRef &ref)
set gsftrack reference
reco::ElectronSeedRef electronSeed
XYZVectorD XYZVector
spatial vector with cartesian internal representation
void associatedElements(unsigned i, const LinkData &linkData, std::multimap< double, unsigned > &sortedAssociates, reco::PFBlockElement::Type type=PFBlockElement::NONE, LinkTest test=LINKTEST_RECHIT) const
XYZPointD XYZPoint
point in space with cartesian internal representation
void addPreshowerCluster(const CaloClusterPtr &r)
add reference to constituent BasicCluster
void linkRefinableObjectGSFTracksToKFs(ProtoEGObject &)
std::vector< std::pair< unsigned int, unsigned int > > convGsfTrack_
void setSuperClusterPFECALRef(reco::SuperClusterRef sc)
set reference to the corresponding supercluster
void addConversionRef(const reco::ConversionRef &convref)
add Conversions from PF
std::vector< Item >::const_iterator const_iterator
std::vector< PFKFFlaggedElement > primaryKFs
std::unordered_map< const PFClusterElement *, std::vector< PFClusterFlaggedElement > > ClusterMap
void addCluster(const CaloClusterPtr &r)
add reference to constituent BasicCluster
ElementMap _recoveredlinks
void fillPFCandidates(const pfEGHelpers::HeavyObjectCache *hoc, const std::list< ProtoEGObject > &, reco::PFCandidateCollection &, reco::PFCandidateEGammaExtraCollection &)
void removeOrLinkECALClustersToKFTracks()
Particle reconstructed by the particle flow algorithm.
reco::SuperCluster buildRefinedSuperCluster(const ProtoEGObject &)
void unlinkRefinableObjectKFandECALMatchedToHCAL(ProtoEGObject &, bool removeFreeECAL=false, bool removeSCECAL=false)
std::pair< const PFKFElement *, bool > PFKFFlaggedElement
void mergeROsByAnyLink(std::list< ProtoEGObject > &)
void RunPFEG(const pfEGHelpers::HeavyObjectCache *hoc, const reco::PFBlockRef &blockRef, std::vector< bool > &active)
const PFRecTrackRef & trackRefPF() const override
void setSuperClusterRef(const reco::SuperClusterRef &scRef)
int attachPSClusters(const PFClusterElement *, ClusterMap::mapped_type &)
void linkRefinableObjectKFTracksToECAL(ProtoEGObject &)
void setKfTrackRef(const reco::TrackRef &ref)
set kf track reference
const CaloClusterPtr & seed() const
seed BasicCluster
void setMVA(float val)
set the result (mostly for debugging)
void linkRefinableObjectSecondaryKFsToECAL(ProtoEGObject &)
void setLateBrem(float val)
set LateBrem
trackRef_iterator tracks_begin() const
first iterator over tracks
reco::PFCandidateCollection _finalCandidates
void linkRefinableObjectConvSecondaryKFsToSecondaryKFs(ProtoEGObject &)
verbosityLevel verbosityLevel_
void setTrackRef(const reco::TrackRef &ref)
set track reference
reco::PFCandidateCollection outcands_
bool next_combination(BidIt n_begin, BidIt n_end, BidIt r_begin, BidIt r_end)
void setTime(float time, float timeError=0.f)
the timing information
void setPdgId(int pdgId) final
void setPreshowerEnergyPlane1(double preshowerEnergy1)
std::vector< PFGSFFlaggedElement > primaryGSFs
void setP4(const LorentzVector &p4) final
set 4-momentum
const ESChannelStatus * channelStatus_
CaloCluster_iterator preshowerClustersEnd() const
last iterator over PreshowerCluster constituents
void addExtraNonConvTrack(const reco::PFBlockRef &blk, const reco::PFBlockElementTrack &tkref)
track counting for electrons and photons
void setPreshowerEnergy(double preshowerEnergy)
void linkRefinableObjectPrimaryGSFTrackToHCAL(ProtoEGObject &)