47 ATH_CHECK(container.record(std::make_unique<xAOD::TrackParticleContainer>(), std::make_unique<xAOD::TrackParticleAuxContainer>()));
50 std::vector<std::vector<const Muon::MdtPrepData*> > SortedMdt;
54 if (nMDT <= 0) {
return StatusCode::SUCCESS; }
68 std::vector<TrackletSegment> segs[6][2][16];
69 std::vector<std::vector<const Muon::MdtPrepData*> >
::const_iterator ChamberItr = SortedMdt.begin();
70 for (; ChamberItr != SortedMdt.end(); ++ChamberItr) {
71 std::vector<TrackletSegment> mlsegments;
72 std::vector<const Muon::MdtPrepData*>::const_iterator mdt1 = ChamberItr->begin();
73 std::vector<const Muon::MdtPrepData*>::const_iterator mdtEnd = ChamberItr->end();
78 bool mdt1_isBarrel =
m_idHelperSvc->mdtIdHelper().isBarrel(mdt1_ID);
79 bool mdt1_isEndcap =
m_idHelperSvc->mdtIdHelper().isEndcap(mdt1_ID);
81 int maxLayer =
m_idHelperSvc->mdtIdHelper().tubeLayerMax(mdt1_ID);
85 for (; mdt1 != mdtEnd; ++mdt1) {
93 if (tl1 == maxLayer)
break;
96 std::vector<const Muon::MdtPrepData*>::const_iterator mdt2 = (mdt1 + 1);
97 if (mdt2 == mdtEnd)
continue;
99 for (; mdt2 != mdtEnd; ++mdt2) {
108 if (mdt1 == mdt2 || (tl2 - tl1) > 1 || (tl2 - tl1) < 0)
continue;
109 if ((tl2 - tl1) == 0 && (
m_idHelperSvc->mdtIdHelper().tube(mdt2_ID) -
112 if (mdt1_isBarrel && std::abs((*mdt1)->globalPosition().z() - (*mdt2)->globalPosition().z()) >
m_d12_max)
continue;
113 if (mdt1_isEndcap && std::abs((*mdt1)->globalPosition().perp() - (*mdt2)->globalPosition().perp()) >
m_d12_max)
continue;
116 std::vector<const Muon::MdtPrepData*>::const_iterator mdt3 = (mdt2 + 1);
117 if (mdt3 == mdtEnd)
continue;
119 for (; mdt3 != mdtEnd; ++mdt3) {
127 if (mdt1 == mdt3 || mdt2 == mdt3)
continue;
129 if ((tl3 - tl2) > 1 || (tl3 - tl2) < 0 || (tl3 - tl1) <= 0)
continue;
130 if ((tl3 - tl2) == 0 && (
m_idHelperSvc->mdtIdHelper().tube(mdt3_ID) -
133 if (mdt1_isBarrel && std::abs((*mdt1)->globalPosition().z() - (*mdt3)->globalPosition().z()) >
m_d13_max)
continue;
134 if (mdt1_isEndcap && std::abs((*mdt1)->globalPosition().perp() - (*mdt3)->globalPosition().perp()) >
m_d13_max)
continue;
137 std::vector<const Muon::MdtPrepData*> mdts;
138 mdts.push_back((*mdt1));
139 mdts.push_back((*mdt2));
140 mdts.push_back((*mdt3));
142 for (
const TrackletSegment &tmpSeg : tmpSegs) mlsegments.push_back(tmpSeg);
149 int stationRegion =
m_idHelperSvc->mdtIdHelper().stationRegion(mdt1_ID);
151 if (stationRegion == 0)
152 for (
const TrackletSegment &mlsegment : mlsegments) segs[0][ML - 1][sector - 1].push_back(mlsegment);
153 else if (stationRegion == 2)
154 for (
const TrackletSegment &mlsegment : mlsegments) segs[1][ML - 1][sector - 1].push_back(mlsegment);
155 else if (stationRegion == 3)
156 for (
const TrackletSegment &mlsegment : mlsegments) segs[2][ML - 1][sector - 1].push_back(mlsegment);
158 else if (mdt1_isEndcap){
159 if (stationRegion == 0)
160 for (
const TrackletSegment &mlsegment : mlsegments) segs[3][ML - 1][sector - 1].push_back(mlsegment);
161 else if (stationRegion == 2)
162 for (
const TrackletSegment &mlsegment : mlsegments) segs[4][ML - 1][sector - 1].push_back(mlsegment);
163 else if (stationRegion == 3)
164 for (
const TrackletSegment &mlsegment : mlsegments) segs[5][ML - 1][sector - 1].push_back(mlsegment);
171 std::vector<TrackletSegment> CleanSegs[6][2][16];
172 for (
int st = 0; st < 6; ++st) {
173 for (
int ml = 0; ml < 2; ++ml) {
174 for (
int sector = 0; sector < 16; ++sector) {
175 if (!segs[st][ml][sector].
empty()) {
176 CleanSegs[st][ml][sector] =
CleanSegments(segs[st][ml][sector]);
183 for (
int st = 0; st < 6; ++st) {
185 for (
int sector = 0; sector < 16; ++sector) {
188 const Identifier trkID = ML1seg.getIdentifier();
191 int stationRegion =
m_idHelperSvc->mdtIdHelper().stationRegion(trkID);
194 if (stationRegion == 0){
196 else DeltaAlphaCut =
c_BIL / 750.0;
198 else if (stationRegion == 2){
200 else DeltaAlphaCut =
c_BML / 750.0;
202 else if (stationRegion == 3){
204 else DeltaAlphaCut =
c_BOL / 750.0;
213 if (ML1seg.mdtChamber() != ML2seg.mdtChamber() || ML1seg.mdtChEta() != ML2seg.mdtChEta())
continue;
215 double deltaAlpha = ML1seg.alpha() - ML2seg.alpha();
218 if (std::abs(deltaAlpha) < DeltaAlphaCut && goodDeltab) {
221 double charge_discriminant = deltaAlpha * ML1seg.globalPosition().z() * std::tan(ML1seg.alpha());
222 double charge = charge_discriminant < 0 ? -1 : 1;
224 double pTot =
TrackMomentum(ML1seg.getIdentifier(), deltaAlpha);
229 std::vector<const Muon::MdtPrepData*> mdts = ML1seg.mdtHitsOnTrack();
230 std::vector<const Muon::MdtPrepData*> mdts2 = ML2seg.mdtHitsOnTrack();
234 if (!CombinedSeg.empty()) {
237 double pT = pTot * std::sin(CombinedSeg[0].alpha());
238 double pz = pTot * std::cos(CombinedSeg[0].alpha());
239 Amg::Vector3D momentum(pT * std::cos(CombinedSeg[0].globalPosition().
phi()),
240 pT * std::sin(CombinedSeg[0].globalPosition().
phi()),
244 matrix.setIdentity();
245 matrix(0, 0) = std::pow(CombinedSeg[0].rError(),2);
246 matrix(1, 1) = std::pow(CombinedSeg[0].zError(),2);
247 matrix(2, 2) = std::pow(0.00000000001,2);
249 matrix(3, 3) = std::pow(CombinedSeg[0].alphaError(),2);
250 matrix(4, 4) = std::pow(Trk1overPErr,2);
252 ATH_MSG_DEBUG(
"Track " << tracklets.size() <<
" found with p = (" << momentum.x() <<
", "
253 << momentum.y() <<
", " << momentum.z()
254 <<
") and |p| = " << tmpTrk.
momentum().mag() <<
" MeV");
255 tracklets.push_back(tmpTrk);
260 double pT = pTot * std::sin(ML1seg.alpha());
261 double pz = pTot * std::cos(ML1seg.alpha());
262 Amg::Vector3D momentum(pT * std::cos(ML1seg.globalPosition().phi()),
263 pT * std::sin(ML1seg.globalPosition().phi()),
267 matrix.setIdentity();
268 matrix(0, 0) = std::pow(ML1seg.rError(),2);
269 matrix(1, 1) = std::pow(ML1seg.zError(),2);
270 matrix(2, 2) = std::pow(0.00000000001,2);
272 matrix(3, 3) = std::pow(ML1seg.alphaError(),2);
273 matrix(4, 4) = std::pow(Trk1overPErr,2);
275 ATH_MSG_DEBUG(
"Track " << tracklets.size() <<
" found with p = (" << momentum.x() <<
", "
276 << momentum.y() <<
", " << momentum.z()
277 <<
") and |p| = " << tmpTrk.
momentum().mag() <<
" MeV");
278 tracklets.push_back(tmpTrk);
284 std::vector<const Muon::MdtPrepData*> mdts = ML1seg.mdtHitsOnTrack();
285 std::vector<const Muon::MdtPrepData*> mdts2 = ML2seg.mdtHitsOnTrack();
289 if (!CombinedSeg.empty()) {
292 double pT = pTot * std::sin(CombinedSeg[0].alpha());
293 double pz = pTot * std::cos(CombinedSeg[0].alpha());
294 Amg::Vector3D momentum(pT * std::cos(CombinedSeg[0].globalPosition().
phi()),
295 pT * std::sin(CombinedSeg[0].globalPosition().
phi()),
299 matrix.setIdentity();
300 matrix(0, 0) = std::pow(CombinedSeg[0].rError(),2);
301 matrix(1, 1) = std::pow(CombinedSeg[0].zError(),2);
302 matrix(2, 2) = std::pow(0.0000001,2);
304 matrix(3, 3) = std::pow(CombinedSeg[0].alphaError(),2);
308 tracklets.push_back(tmpTrk);
325 return StatusCode::SUCCESS;
466 std::vector<std::pair<double, double> > SeedParams;
476 double x1 = mdts.front()->globalPosition().z();
477 double y1 = mdts.front()->globalPosition().perp();
478 double r1 = std::abs(mdts.front()->localPosition()[
Trk::locR]);
480 double x2 = mdts.back()->globalPosition().z();
481 double y2 = mdts.back()->globalPosition().perp();
482 double r2 = std::abs(mdts.back()->localPosition()[
Trk::locR]);
484 double DeltaX = x2 - x1;
485 double DeltaY = y2 - y1;
486 double DistanceOfCenters = std::hypot(DeltaX, DeltaY);
487 if (DistanceOfCenters < 30)
return SeedParams;
488 double Alpha0 = std::acos(DeltaX / DistanceOfCenters);
491 double phi = mdts.front()->globalPosition().phi();
492 double RSum = r1 + r2;
493 if (RSum > DistanceOfCenters)
return SeedParams;
494 double Alpha1 = std::asin(RSum / DistanceOfCenters);
495 double line_theta = Alpha0 + Alpha1;
496 double z_line = x1 + r1 * std::sin(line_theta);
497 double rho_line = y1 - r1 * std::cos(line_theta);
500 Amg::Vector3D gDir(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
501 Amg::Vector3D globalDir1(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
502 double gSlope1 = (globalDir1.perp() / globalDir1.z());
503 double gInter1 = gPos1.perp() - gSlope1 * gPos1.z();
505 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope1, gInter1);
507 line_theta = Alpha0 - Alpha1;
508 z_line = x1 - r1 * std::sin(line_theta);
509 rho_line = y1 + r1 * std::cos(line_theta);
511 Amg::Vector3D globalDir2(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
512 double gSlope2 = (globalDir2.perp() / globalDir2.z());
513 double gInter2 = gPos2.perp() - gSlope2 * gPos2.z();
515 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope2, gInter2);
517 double Alpha2 = std::asin(std::abs(r2 - r1) / DistanceOfCenters);
520 line_theta = Alpha0 + Alpha2;
521 z_line = x1 - r1 * std::sin(line_theta);
522 rho_line = y1 + r1 * std::cos(line_theta);
525 Amg::Vector3D globalDir3(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
526 double gSlope3 = (globalDir3.perp() / globalDir3.z());
527 double gInter3 = gPos3.perp() - gSlope3 * gPos3.z();
529 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope3, gInter3);
532 line_theta = Alpha0 - Alpha2;
533 z_line = x1 + r1 * std::sin(line_theta);
534 rho_line = y1 - r1 * std::cos(line_theta);
537 Amg::Vector3D globalDir4(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
538 double gSlope4 = (globalDir4.perp() / globalDir4.z());
539 double gInter4 = gPos4.perp() - gSlope4 * gPos4.z();
541 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope4, gInter4);
544 line_theta = Alpha0 + Alpha2;
545 z_line = x1 + r1 * std::sin(line_theta);
546 rho_line = y1 - r1 * std::cos(line_theta);
549 Amg::Vector3D globalDir3(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
550 double gSlope3 = (globalDir3.perp() / globalDir3.z());
551 double gInter3 = gPos3.perp() - gSlope3 * gPos3.z();
553 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope3, gInter3);
556 line_theta = Alpha0 - Alpha2;
557 z_line = x1 - r1 * std::sin(line_theta);
558 rho_line = y1 + r1 * std::cos(line_theta);
561 Amg::Vector3D globalDir4(std::cos(
phi) * std::sin(line_theta), std::sin(
phi) * std::sin(line_theta), std::cos(line_theta));
562 double gSlope4 = (globalDir4.perp() / globalDir4.z());
563 double gInter4 = gPos4.perp() - gSlope4 * gPos4.z();
565 if (resid <
m_SeedResidual) SeedParams.emplace_back(gSlope4, gInter4);
589 const std::vector<std::pair<double, double> >& SeedParams)
const {
590 std::vector<TrackletSegment> segs;
593 for (
const std::pair<double,double> &SeedParam : SeedParams) {
597 double s(0),
sz(0), sy(0);
604 const double mdt_y = std::hypot(prd->globalPosition().x(), prd->globalPosition().y());
605 const double mdt_z = prd->globalPosition().z();
608 sz += mdt_z / sigma2;
609 sy += mdt_y / sigma2;
611 const double yc = sy / s;
612 const double zc =
sz / s;
615 double alpha = std::atan2(SeedParam.first, 1.0);
616 if (alpha < 0) alpha +=
M_PI;
618 double d = (SeedParam.second - yc + zc * SeedParam.first) * std::cos(alpha);
622 if (std::abs(std::cos(alpha)) > 0.97 && (
m_idHelperSvc->mdtIdHelper().isBarrel(mdtID)))
continue;
623 if (std::abs(std::cos(alpha)) < 0.03 && (
m_idHelperSvc->mdtIdHelper().isEndcap(mdtID)))
continue;
626 double sPyy(0), sPyz(0), sPyyzz(0);
628 double mdt_y = std::hypot(prd->globalPosition().x(), prd->globalPosition().y());
629 double mdt_z = prd->globalPosition().z();
631 sPyy += std::pow(mdt_y-yc,2) / sigma2;
632 sPyz += (mdt_y - yc) * (mdt_z - zc) / sigma2;
633 sPyyzz += ((mdt_y - yc) - (mdt_z - zc)) * ((mdt_y - yc) + (mdt_z - zc)) / sigma2;
638 double deltaAlpha = 0;
641 double sumRyi(0), sumRzi(0), sumRi(0);
644 const double cos_a = std::cos(alpha);
645 const double sin_a = std::sin(alpha);
647 double mdt_y = prd->globalPosition().perp();
648 double mdt_z = prd->globalPosition().z();
649 double yPi = -(mdt_z - zc) * sin_a + (mdt_y - yc) * cos_a - d;
650 double signR = yPi >= 0 ? -1. : 1;
652 double ri = signR * prd->localPosition()[
Trk::locR];
653 sumRyi += ri * (mdt_y - yc) / sigma2;
654 sumRzi += ri * (mdt_z - zc) / sigma2;
655 sumRi += ri / sigma2;
656 chi2 += std::pow(yPi+ri,2) / sigma2;
658 double bAlpha = -1 * sPyz + cos_a * (sin_a * sPyyzz + 2 * cos_a * sPyz + sumRzi) + sin_a * sumRyi;
659 double AThTh = sPyy + cos_a * (2 * sin_a * sPyz - cos_a * sPyyzz);
663 if (std::abs(AThTh) < 1.e-7)
break;
665 double alphaNew = alpha + bAlpha / AThTh;
666 double dNew = sumRi / s;
668 dalpha = std::sqrt(1 / std::abs(AThTh));
669 dd = std::sqrt(1 / s);
670 deltaAlpha = std::abs(alphaNew - alpha);
671 deltad = std::abs(d - dNew);
673 if (deltaAlpha < 5.e-7 && deltad < 5.e-6)
break;
677 if (Nitr > 10)
break;
681 double chi2Prob = TMath::Prob(
chi2, mdts.size() - 2);
684 double z0 = zc - d * std::sin(alpha);
685 double dz0 = std::hypot(dd*std::sin(alpha), d*dalpha*std::cos(alpha));
686 double y0 = yc + d * std::cos(alpha);
687 double dy0 = std::hypot(dd*std::cos(alpha), d*dalpha*std::sin(alpha));
698 for (
unsigned int k = 0; k < mdts.size(); ++k) {
699 int base = std::pow(10, k);
700 double mdtR = std::hypot(mdts.at(k)->globalPosition().x(), mdts.at(k)->globalPosition().y());
701 double mdtZ = mdts.at(k)->globalPosition().z();
702 double zTest = (mdtR - y0) / std::tan(alpha) + z0 - mdtZ;
711 double mdtPhi = mdts.at(0)->globalPosition().phi();
712 Amg::Vector3D segpos(y0 * std::cos(mdtPhi), y0 * std::sin(mdtPhi), z0);
715 segs.push_back(MyTrackletSegment);
716 if (pattern == -1)
break;
721 if (segs.size() > 1) {
722 std::vector<TrackletSegment> tmpSegs;
723 for (
unsigned int i1 = 0; i1 < segs.size(); ++i1) {
724 bool isUnique =
true;
725 int pattern1 = segs.at(i1).getHitPattern();
726 for (
unsigned int i2 = (i1 + 1); i2 < segs.size(); ++i2) {
727 if (pattern1 == -1)
break;
728 int pattern2 = segs.at(i2).getHitPattern();
729 if (pattern1 == pattern2) isUnique =
false;
731 if (isUnique) tmpSegs.push_back(segs.at(i1));
743 std::vector<TrackletSegment> CleanSegs;
744 std::vector<TrackletSegment> segs = Segs;
745 bool keepCleaning(
true);
748 while (keepCleaning) {
750 keepCleaning =
false;
752 for (std::vector<TrackletSegment>::iterator it = segs.begin(); it != segs.end(); ++it) {
753 if (it->isCombined())
continue;
754 std::vector<TrackletSegment> segsToCombine;
755 double tanTh1 = std::tan(it->alpha());
756 double r1 = it->globalPosition().perp();
757 double zi1 = it->globalPosition().z() - r1 / tanTh1;
759 for (std::vector<TrackletSegment>::iterator sit = (it + 1); sit != segs.end(); ++sit) {
760 if (sit->isCombined())
continue;
761 if (it->mdtChamber() != sit->mdtChamber())
continue;
762 if ((it->mdtChEta()) * (sit->mdtChEta()) < 0)
continue;
763 if (it->mdtChPhi() != sit->mdtChPhi())
continue;
764 if (std::abs(it->alpha() - sit->alpha()) > 0.005)
continue;
765 double tanTh2 = std::tan(sit->alpha());
766 double r2 = sit->globalPosition().perp();
767 double zi2 = sit->globalPosition().z() - r2 / tanTh2;
769 double rmid = (r1 + r2) / 2.;
770 double z1 = rmid / tanTh1 + zi1;
771 double z2 = rmid / tanTh2 + zi2;
772 double zdist = std::abs(z1 - z2);
774 segsToCombine.push_back(*sit);
775 sit->isCombined(
true);
780 if (segsToCombine.empty()) {
781 CleanSegs.push_back(*it);
784 else if (!segsToCombine.empty()) {
786 std::vector<const Muon::MdtPrepData*> mdts = it->mdtHitsOnTrack();
788 std::vector<const Muon::MdtPrepData*> tmpmdts = seg.mdtHitsOnTrack();
792 if (tmpprd->identify() == tmpprd2->identify()) {
802 if (mdts.size() > it->mdtHitsOnTrack().size()) {
805 if (refitsegs.empty()) {
806 if (segsToCombine.size() == 1) {
807 segsToCombine[0].isCombined(
false);
808 CleanSegs.push_back(*it);
809 CleanSegs.push_back(segsToCombine[0]);
812 std::vector<int> nSeg;
813 for (
unsigned int i = 0; i < mdts.size(); ++i) {
816 for (
unsigned int k = 0; k < it->mdtHitsOnTrack().
size(); ++k) {
817 if (it->mdtHitsOnTrack()[k]->identify() == mdts[i]->identify()) {
823 for (
unsigned int k = 0; k < segsToCombine.size(); ++k) {
824 for (
unsigned int m = 0; m < segsToCombine[k].mdtHitsOnTrack().
size(); ++m) {
825 if (segsToCombine[k].mdtHitsOnTrack()[m]->identify() == mdts[i]->identify()) {
834 bool keeprefitting(
true);
836 while (keeprefitting) {
838 int nMinSeg(nSeg[0]);
840 std::vector<int> nrfsegs;
841 std::vector<const Muon::MdtPrepData*> refitmdts;
843 for (
unsigned int i = 1; i < mdts.size(); ++i) {
844 if (nSeg[i] < nMinSeg) {
845 refitmdts.push_back(minmdt);
846 nrfsegs.push_back(nMinSeg);
850 refitmdts.push_back(mdts[i]);
851 nrfsegs.push_back(nSeg[i]);
859 if (!refitsegs.empty()) {
860 for (
const TrackletSegment &refitseg : refitsegs) CleanSegs.push_back(refitseg);
861 keeprefitting =
false;
862 }
else if (mdts.size() <= 3) {
863 CleanSegs.push_back(*it);
864 keeprefitting =
false;
866 if (nItr2 > 10)
break;
871 for (
const TrackletSegment &refitseg : refitsegs) CleanSegs.push_back(refitseg);
876 CleanSegs.push_back(*it);
883 if (nItr > 10)
break;
1018 std::vector<Tracklet> myTracks = tracks;
1020 for (
const Tracklet &track : myTracks) {
1021 Identifier id1 = track.getML1seg().mdtHitsOnTrack().at(0)->identify();
1022 Identifier id2 = track.getML2seg().mdtHitsOnTrack().at(0)->identify();
1023 int nLayerML1 =
m_idHelperSvc->mdtIdHelper().tubeLayerMax(id1);
1024 int nLayerML2 =
m_idHelperSvc->mdtIdHelper().tubeLayerMax(id2);
1025 double ratio = (double)(track.mdtHitsOnTrack().size()) / (nLayerML1 + nLayerML2);
1026 if (ratio > 0.75) tracks.push_back(track);
1030 std::vector<Tracklet> UniqueTracks;
1031 std::vector<unsigned int> AmbigTrks;
1032 for (
unsigned int tk1 = 0; tk1 < tracks.size(); ++tk1) {
1035 bool isResolved =
false;
1036 for (
unsigned int AmbigTrksIdx : AmbigTrks) {
1037 if (tk1 == AmbigTrksIdx) {
1042 if (isResolved)
continue;
1043 std::vector<Tracklet> AmbigTracks;
1044 AmbigTracks.push_back(tracks.at(tk1));
1046 double Trk1ML1R = tracks.at(tk1).getML1seg().globalPosition().perp();
1047 double Trk1ML1Z = tracks.at(tk1).getML1seg().globalPosition().z();
1048 double Trk1ML2R = tracks.at(tk1).getML2seg().globalPosition().perp();
1049 double Trk1ML2Z = tracks.at(tk1).getML2seg().globalPosition().z();
1051 Identifier tk1ID = tracks.at(tk1).muonIdentifier();
1052 bool tk1_isBarrel =
m_idHelperSvc->mdtIdHelper().isBarrel(tk1ID);
1053 bool tk1_isEndcap =
m_idHelperSvc->mdtIdHelper().isEndcap(tk1ID);
1056 for (
unsigned int tk2 = (tk1 + 1); tk2 < tracks.size(); ++tk2) {
1057 if (tracks.at(tk1).mdtChamber() == tracks.at(tk2).mdtChamber() && tracks.at(tk1).mdtChPhi() == tracks.at(tk2).mdtChPhi() &&
1058 (tracks.at(tk1).mdtChEta()) * (tracks.at(tk2).mdtChEta()) > 0) {
1060 for (
unsigned int AmbigTrksIdx : AmbigTrks) {
1061 if (tk2 == AmbigTrksIdx) {
1066 if (isResolved)
continue;
1068 double Trk2ML1R = tracks.at(tk2).getML1seg().globalPosition().perp();
1069 double Trk2ML1Z = tracks.at(tk2).getML1seg().globalPosition().z();
1070 double Trk2ML2R = tracks.at(tk2).getML2seg().globalPosition().perp();
1071 double Trk2ML2Z = tracks.at(tk2).getML2seg().globalPosition().z();
1074 double DistML1(1000), DistML2(1000);
1076 DistML1 = std::abs(Trk1ML1Z - Trk2ML1Z);
1077 DistML2 = std::abs(Trk1ML2Z - Trk2ML2Z);
1078 }
else if (tk1_isEndcap) {
1079 DistML1 = std::abs(Trk1ML1R - Trk2ML1R);
1080 DistML2 = std::abs(Trk1ML2R - Trk2ML2R);
1082 if (DistML1 < 40 || DistML2 < 40) {
1084 std::vector<const Muon::MdtPrepData*> mdts1 = tracks.at(tk1).mdtHitsOnTrack();
1085 std::vector<const Muon::MdtPrepData*> mdts2 = tracks.at(tk2).mdtHitsOnTrack();
1089 if (mdt1->identify() == mdt2->identify()) {
1096 if (nShared <= 1)
continue;
1098 AmbigTracks.push_back(tracks.at(tk2));
1099 AmbigTrks.push_back(tk2);
1104 if (AmbigTracks.size() == 1) {
1105 UniqueTracks.push_back(tracks.at(tk1));
1111 bool hasMomentum = tracks.at(tk1).charge() != 0;
1112 double aveX(0), aveY(0), aveZ(0), aveAlpha(0);
1113 double aveP(0), nAmbigP(0), TrkCharge(tracks.at(tk1).charge());
1114 bool allSameSign(
true);
1116 for (
const Tracklet &AmbigTrack : AmbigTracks) {
1118 aveX += AmbigTrack.globalPosition().x();
1119 aveY += AmbigTrack.globalPosition().y();
1120 aveZ += AmbigTrack.globalPosition().z();
1121 aveAlpha += AmbigTrack.getML1seg().alpha();
1124 if (std::abs(AmbigTrack.charge() - TrkCharge) > 0.1) allSameSign =
false;
1126 aveP += AmbigTrack.momentum().mag();
1128 aveAlpha += AmbigTrack.alpha();
1129 aveX += AmbigTrack.globalPosition().x();
1130 aveY += AmbigTrack.globalPosition().y();
1131 aveZ += AmbigTrack.globalPosition().z();
1135 aveX = aveX / (double)AmbigTracks.size();
1136 aveY = aveY / (double)AmbigTracks.size();
1137 aveZ = aveZ / (double)AmbigTracks.size();
1139 aveAlpha = aveAlpha / (double)AmbigTracks.size();
1140 double alphaErr = tracks.at(tk1).getML1seg().alphaError();
1141 double rErr = tracks.at(tk1).getML1seg().rError();
1142 double zErr = tracks.at(tk1).getML1seg().zError();
1151 matrix.setIdentity();
1152 matrix(0, 0) = std::pow(tracks.at(tk1).getML1seg().rError(),2);
1153 matrix(1, 1) = std::pow(tracks.at(tk1).getML1seg().zError(),2);
1154 matrix(2, 2) = std::pow(0.0000001,2);
1155 matrix(3, 3) = std::pow(tracks.at(tk1).getML1seg().alphaError(),2);
1157 Tracklet aveTrack(aveSegML1, momentum, matrix, 0);
1158 UniqueTracks.push_back(aveTrack);
1159 }
else if (allSameSign) {
1160 aveP = aveP / nAmbigP;
1161 double pT = aveP * std::sin(tracks.at(tk1).getML1seg().alpha());
1162 double pz = aveP * std::cos(tracks.at(tk1).getML1seg().alpha());
1163 Amg::Vector3D momentum(pT * std::cos(tracks.at(tk1).globalPosition().phi()),
1164 pT * std::sin(tracks.at(tk1).globalPosition().phi()),
1168 MyTrack.
charge(tracks.at(tk1).charge());
1169 UniqueTracks.push_back(MyTrack);
1171 aveX = aveX / (double)AmbigTracks.size();
1172 aveY = aveY / (double)AmbigTracks.size();
1173 aveZ = aveZ / (double)AmbigTracks.size();
1175 aveAlpha = aveAlpha / (double)AmbigTracks.size();
1176 double alphaErr = tracks.at(tk1).getML1seg().alphaError();
1177 double rErr = tracks.at(tk1).getML1seg().rError();
1178 double zErr = tracks.at(tk1).getML1seg().zError();
1187 matrix.setIdentity();
1188 matrix(0, 0) = std::pow(tracks.at(tk1).getML1seg().rError(),2);
1189 matrix(1, 1) = std::pow(tracks.at(tk1).getML1seg().zError(),2);
1190 matrix(2, 2) = std::pow(0.0000001,2);
1191 matrix(3, 3) = std::pow(tracks.at(tk1).getML1seg().alphaError(),2);
1193 Tracklet aveTrack(aveSegML1, momentum, matrix, 0);
1194 UniqueTracks.push_back(aveTrack);
1199 else if (tk1_isEndcap) {
1200 std::vector<const Muon::MdtPrepData*> AllMdts;
1201 for (
Tracklet const &AmbigTrack : AmbigTracks) {
1202 std::vector<const Muon::MdtPrepData*> mdts = AmbigTrack.mdtHitsOnTrack();
1203 std::vector<const Muon::MdtPrepData*> tmpAllMdt = AllMdts;
1205 bool isNewHit =
true;
1207 if (mdt->identify() == tmpmdt->identify()) {
1212 if (isNewHit) AllMdts.push_back(mdt);
1217 if (!MyECsegs.empty()) {
1226 matrix.setIdentity();
1227 matrix(0, 0) = std::pow(ECseg.
rError(),2);
1228 matrix(1, 1) = std::pow(ECseg.
zError(),2);
1229 matrix(2, 2) = std::pow(0.0000001,2);
1230 matrix(3, 3) = std::pow(ECseg.
alphaError(),2);
1232 Tracklet MyCombTrack(MyECsegs.at(0), ECseg, momentum, matrix, 0);
1233 UniqueTracks.push_back(MyCombTrack);
1235 UniqueTracks.push_back(tracks.at(tk1));
1240 return UniqueTracks;