8 #include "AthLinks/ElementLink.h"
23 m_deco_charge(
"charge"),
26 m_deco_sig3D(
"significance3D"),
27 m_deco_deltaR(
"deltaR"),
30 m_deco_eFrac(
"efracsv"),
31 m_deco_nHFTracks(
"nHFtrk"){
32 declareInterface<IGNNVertexFitterInterface>(
this);
52 std::string linkNameMod =
"";
63 return StatusCode::SUCCESS;
68 TLorentzVector
sum(0., 0., 0., 0.);
69 for (
int i = 0;
i < (
int)selTrk.size(); ++
i) {
70 if (selTrk[
i] == NULL)
72 sum += selTrk[
i]->p4();
79 const std::vector<double> &secVrtErr,
double &signif)
const {
80 double distx = primVrt.
x() - secVrt.x();
81 double disty = primVrt.
y() - secVrt.y();
82 double distz = primVrt.
z() - secVrt.z();
84 AmgSymMatrix(3) primCovMtx = primVrt.covariancePosition();
85 primCovMtx(0, 0) += secVrtErr[0];
86 primCovMtx(0, 1) += secVrtErr[1];
87 primCovMtx(1, 0) += secVrtErr[1];
88 primCovMtx(1, 1) += secVrtErr[2];
89 primCovMtx(0, 2) += secVrtErr[3];
90 primCovMtx(2, 0) += secVrtErr[3];
91 primCovMtx(1, 2) += secVrtErr[4];
92 primCovMtx(2, 1) += secVrtErr[4];
93 primCovMtx(2, 2) += secVrtErr[5];
97 signif = distx * wgtMtx(0, 0) * distx + disty * wgtMtx(1, 1) * disty + distz * wgtMtx(2, 2) * distz +
98 2. * distx * wgtMtx(0, 1) * disty + 2. * distx * wgtMtx(0, 2) * distz + 2. * disty * wgtMtx(1, 2) * distz;
99 signif = std::sqrt(std::abs(signif));
100 if (signif != signif)
102 return std::sqrt(distx * distx + disty * disty + distz * distz);
108 const xAOD::Vertex &primVrt,
const EventContext &ctx)
const {
110 using TLC = std::vector<ElementLink<DataVector<xAOD::TrackParticle_v1>>>;
121 for (
const auto &
jet : *inJetContainer) {
124 auto vertexCollection = vertexLinksHandle(*
jet);
125 auto trackCollection = trackLinksHandle(*
jet);
126 auto trackOriginCollection = trackOriginsHandle(*
jet);
128 using indexList = std::vector<int>;
129 using trackCountMap = std::map<char, std::set<TL>>;
131 indexList iList(vertexCollection.size());
133 trackCountMap allTracksMap;
134 trackCountMap heavyFlavourVertexMap;
135 trackCountMap primaryVertexMap;
136 trackCountMap fittingMap;
139 heavyFlavourVertexMap.clear();
140 primaryVertexMap.clear();
141 allTracksMap.clear();
147 auto trackOrigin = trackOriginCollection[
index];
148 auto trackLink = trackCollection[
index];
150 allTracksMap[
vertex].insert(trackLink);
155 heavyFlavourVertexMap[
vertex].insert(trackLink);
159 primaryVertexMap[
vertex].insert(trackLink);
164 auto pvCandidate = std::max_element(
165 primaryVertexMap.begin(), primaryVertexMap.end(),
166 [](
const auto&
a,
const auto&
b) { return a.second.size() < b.second.size(); }
170 for (
const auto &vertexTrackPair : allTracksMap) {
172 const auto &[
vertex, trackLinks] = vertexTrackPair;
175 if(
vertex == pvCandidate) {
181 if (heavyFlavourVertexMap.find(
vertex) == heavyFlavourVertexMap.end()) {
187 if (heavyFlavourVertexMap.find(
vertex) != heavyFlavourVertexMap.end() &&
188 (
static_cast<float>(heavyFlavourVertexMap[
vertex].size()) / trackLinks.size()) <
m_HFRatioThres) {
193 fittingMap.insert(std::pair<
char, std::set<TL>>(
vertex, trackLinks));
198 const char mergedVertexKey = 0;
199 std::set<TL> mergedSet;
200 std::set<TL> combinedHFTracks;
203 for (
const auto &vertexTrackPair : fittingMap) {
205 mergedSet.insert(vertexTrackPair.second.begin(), vertexTrackPair.second.end());
206 combinedHFTracks.insert(heavyFlavourVertexMap[vertexTrackPair.first].begin(), heavyFlavourVertexMap[vertexTrackPair.first].end());
211 fittingMap[mergedVertexKey] = std::move(mergedSet);
212 heavyFlavourVertexMap.clear();
213 heavyFlavourVertexMap[mergedVertexKey] = std::move(combinedHFTracks);
221 xAODwrk->beamX = beamSpotHandle->beamPos().x();
222 xAODwrk->beamY = beamSpotHandle->beamPos().y();
223 xAODwrk->beamZ = beamSpotHandle->beamPos().z();
224 xAODwrk->tanBeamTiltX =
tan(beamSpotHandle->beamTilt(0));
225 xAODwrk->tanBeamTiltY =
tan(beamSpotHandle->beamTilt(1));
227 std::unique_ptr<std::vector<WrkVrt>> wrkVrtSet = std::make_unique<std::vector<WrkVrt>>();
231 std::vector<const xAOD::NeutralParticle *> neutralPartDummy(0);
234 for (
const auto &pair : fittingMap) {
236 if (pair.second.size() >= 2) {
237 int NTRKS = pair.second.size();
238 std::vector<double> InpMass(NTRKS,
m_massPi);
241 xAODwrk->listSelTracks.clear();
244 xAODwrk->listSelTracks.push_back(*
TrackLink);
248 TLorentzVector jetDir(
jet->p4());
253 if (
sc.isFailure() || FitVertex.perp() >
m_maxLxy) {
258 vDist = FitVertex - primVrt.
position();
259 double JetVrtDir = jetDir.Px() * vDist.x() + jetDir.Py() * vDist.y() + jetDir.Pz() * vDist.z();
261 JetVrtDir = fabs(JetVrtDir);
271 sc = (
m_vertexFitterTool->VKalVrtFit(xAODwrk->listSelTracks, neutralPartDummy, newvrt.vertex, newvrt.vertexMom,
272 newvrt.vertexCharge, newvrt.vertexCov, newvrt.chi2PerTrk, newvrt.trkAtVrt,
273 newvrt.chi2, *state,
false));
278 auto NDOF = 2 * (newvrt.trkAtVrt.size()) - 3.0;
282 ATH_MSG_DEBUG(
"Found IniVertex=" << newvrt.vertex[0] <<
", " << newvrt.vertex[1] <<
", " << newvrt.vertex[2]
283 <<
" trks " << newvrt.trkAtVrt.size());
290 (vDir.x() * newvrt.vertexMom.Px() + vDir.y() * newvrt.vertexMom.Py() + vDir.z() * newvrt.vertexMom.Pz()) /
291 newvrt.vertexMom.Rho();
293 double Lxy = sqrt(vDir[0] * vDir[0] + vDir[1] * vDir[1]);
294 double Lxyz = sqrt(vDir[0] * vDir[0] + vDir[1] * vDir[1] + vDir[2] * vDir[2]);
299 int ntrk = newvrt.trkAtVrt.size();
301 TLorentzVector MomentumVtx =
TotalMom(xAODwrk->listSelTracks);
303 double eRatio = MomentumVtx.E() /
jet->p4().E();
305 [[maybe_unused]]
double distToPV =
vrtVrtDist(primVrt, newvrt.vertex, newvrt.vertexCov, signif3D);
323 for (
const auto *trk : xAODwrk->listSelTracks) {
327 GNNvertex->addTrackAtVertex(link_trk, 1.);
332 GNNvertex->setPosition(newvrt.vertex);
333 GNNvertex->setFitQuality(newvrt.chi2, NDOF);
336 m_deco_pt(*GNNvertex) = newvrt.vertexMom.Perp();
350 jetWriteDecorHandleVertexLink(*jet).push_back(linkVertex);
355 return StatusCode::SUCCESS;