ATLAS Offline Software
Loading...
Searching...
No Matches
MdtVsTgcRawData_SegmMatching.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2022 CERN for the benefit of the ATLAS collaboration
3*/
4
6// Package : MdtVsTgcRawDataValAlg
7// Author: M.King(Kobe)
8// Feb. 2011
9//
10// DESCRIPTION:
11// Subject: TGC Efficiency -->TGC Efficiency plots including EIFI by comparing with MDT Segments
13
15
21
23
24#include <inttypes.h>
25
26#include <sstream>
27#include <algorithm>
28#include <fstream>
29
30// Matches together segments from different stations into a track
31void
32MdtVsTgcRawDataValAlg::MatchMDTSegments(std::vector<const Muon::MuonSegment*> (&sortedSegments)[2][4],
33 std::vector<const Muon::MuonSegment*> (&disqualifiedSegments)[2][4],
34 std::vector<SegmTrack> (&matchedSegments)[2]){// Define Cuts:
35 // Cut for matching Segments
36 const float dRhoCutSegmentMatching = 1000;
37 const float dPhiCutSegmentMatching = M_PI/8;
38 const float dPhiCutSegmentDirectionChecking[4][4]={{ 0,M_PI/8, 0.1, 0.01},
39 {M_PI/8, 0,M_PI/8,M_PI/8},
40 { 0.06,M_PI/8, 0, 0.01},
41 { 0.05,M_PI/8, 0.05, 0}};
42 const float dTheCutSegmentDirectionChecking[4][4]={{ 0,M_PI/8, 0.05, 0.06},
43 {M_PI/8, 0,M_PI/8,M_PI/8},
44 { 0.04,M_PI/8, 0, 0.005},
45 { 0.02,M_PI/8, 0.005, 0}};
46 // Loop over sides
47 for(int i=0;i<2;i++){// AC
48 bool skipSegm;int nDisqualifiedSegm; // used when checking the disqualified list for a segment
49 //bool HasStationMatchSegm[4] = {false, false, false, false};// flags for whether the there are segments in each MDT station which were included in tracks
50 //bool HasMatchedTrack = false;// flag for whether a track was found on current side
51
52 for(int jMDT1=3;jMDT1>=0;jMDT1--){// MDT Stations in reverse]
53 // Get number of segments
54 int nSegm1=sortedSegments[i][jMDT1].size();
55
56 // Loop over Segments in Station
57 for(int n1=0; n1<nSegm1;n1++){
58 // Get segment
59 const Muon::MuonSegment *segm1 = sortedSegments[i][jMDT1].at(n1);
60
61 // Check disqualifiedSegments for current segment
62 skipSegm=false;
63 nDisqualifiedSegm=disqualifiedSegments[i][jMDT1].size();
64 for(int ndis=0;ndis<nDisqualifiedSegm;ndis++)if(segm1==disqualifiedSegments[i][jMDT1].at(ndis))skipSegm=true;
65 if(skipSegm)continue;
66
67 // Get position variables
68 const Amg::Vector3D segm1Pos = segm1->globalPosition();
69
70 float segm1PosPhi = segm1Pos.phi();
71 float segm1PosZ = segm1Pos.z();
72 if(segm1PosPhi<0)segm1PosPhi+=2*M_PI;
73 Amg::Vector3D segm1PosZunit(segm1Pos/std::abs(segm1PosZ));
74 Amg::Vector3D segm1Dir = segm1->globalDirection();
75
76 float segm1DirThe = segm1Dir.theta();
77 float segm1DirPhi = segm1Dir.phi();
78 if(segm1DirThe>M_PI/2) segm1DirThe=M_PI-segm1DirThe;
79 if(segm1DirPhi<0) segm1DirPhi+=2*M_PI;
80
81 // Initialise segment matching variables
82 bool stationMatchFound[4] = {false,false,false,false};
83 std::vector<const Muon::MuonSegment*> matchingSegments[4];
84 for(int jMDT2=0;jMDT2<4;jMDT2++)matchingSegments[jMDT2] = std::vector<const Muon::MuonSegment*>();
85 matchingSegments[jMDT1].push_back(segm1);
86 int nStationMatch=0;
87
88 for(int jMDT2=3;jMDT2>=0;jMDT2--){// MDT Station in reverse
89 // Get number of segments
90 int nSegm2=sortedSegments[i][jMDT2].size();
91
92 // Loop over Segments in Station
93 for(int n2=0; n2<nSegm2;n2++){
94 // Get segment
95 const Muon::MuonSegment *segm2 = sortedSegments[i][jMDT2].at(n2);
96 if(segm1==segm2)continue; //do not compare same segments
97
98 // Check disqualifiedSegments for current segment
99 skipSegm = false;
100 nDisqualifiedSegm=disqualifiedSegments[i][jMDT2].size();
101 for(int ndis=0;ndis<nDisqualifiedSegm;ndis++)if(segm1==disqualifiedSegments[i][jMDT2].at(ndis))skipSegm=true;
102 if(skipSegm)continue;
103
105 // Position Cut
106 // Fill position variables
107 const Amg::Vector3D segm2Pos = segm2->globalPosition();
108
109 float segm2PosRho = std::abs(segm2Pos.perp());
110 float segm2PosPhi = segm2Pos.phi();
111 float segm2PosThe = segm2Pos.theta();
112 float segm2PosZ = segm2Pos.z();
113 if(segm2PosThe>M_PI/2) segm2PosThe=M_PI-segm2PosThe;
114 if(segm2PosPhi<0)segm2PosPhi+=2*M_PI;
115 Amg::Vector3D segm2PosZunit(segm2Pos/std::abs(segm2PosZ));
116
117 // Apply preliminary phi cut between segm1 and segm2 positions
118 float dPhi_Segm1_Segm2 = segm1PosPhi-segm2PosPhi;
119 if(dPhi_Segm1_Segm2<-M_PI)dPhi_Segm1_Segm2+=2*M_PI;
120 if(dPhi_Segm1_Segm2> M_PI)dPhi_Segm1_Segm2-=2*M_PI;
121 if(std::abs(dPhi_Segm1_Segm2)>dPhiCutSegmentMatching)continue;
122
123 // Extrapolate segm1 position to segm2's Z position
124 float dZ = std::abs(segm2PosZ)-std::abs(segm1PosZ);
125 Amg::Vector3D extrPos(segm1Pos+(segm1PosZunit*dZ));
126
127 float extrPosRho = std::abs(extrPos.perp());
128 float extrPosThe = extrPos.theta();
129 float extrPosPhi = extrPos.phi();
130 if(extrPosThe>M_PI/2) extrPosThe=M_PI-extrPosThe;
131 if(extrPosPhi<0)extrPosPhi+=2*M_PI;
132
133 // Get differences between extrapolated and segm2 positions
134 float dRho_Extr_Segm2 = extrPosRho-segm2PosRho;
135 float dPhi_Extr_Segm2 = extrPosPhi-segm2PosPhi;
136 float dThe_Extr_Segm2 = extrPosThe-segm2PosThe;
137 if(dPhi_Extr_Segm2<-M_PI)dPhi_Extr_Segm2+=2*M_PI;
138 if(dPhi_Extr_Segm2> M_PI)dPhi_Extr_Segm2-=2*M_PI;
139
140 // Fill difference histograms
141 if(m_mdt_segmmatchsag[i][jMDT1][jMDT2][0]) m_mdt_segmmatchsag[i][jMDT1][jMDT2][0]->Fill(dRho_Extr_Segm2);
142 if(m_mdt_segmmatchsag[i][jMDT1][jMDT2][2]) m_mdt_segmmatchsag[i][jMDT1][jMDT2][2]->Fill(dPhi_Extr_Segm2);
143 if(m_mdt_segmmatchsag[i][jMDT1][jMDT2][3]) m_mdt_segmmatchsag[i][jMDT1][jMDT2][3]->Fill(dThe_Extr_Segm2);
144
145 // Cut segments (segm2) which are outside difference cuts
146 if(std::abs(dPhi_Extr_Segm2)>dPhiCutSegmentMatching)continue;
147 if(std::abs(dRho_Extr_Segm2)>dRhoCutSegmentMatching)continue;
148
150 // Direction Cut
151 // Fill direction variables
152 //const Trk::GlobalDirection segm2Dir = segm2->globalDirection();
153 const Amg::Vector3D segm2Dir = segm2->globalDirection();
154
155 float segm2DirThe = segm2Dir.theta();
156 float segm2DirPhi = segm2Dir.phi();
157 if(segm2DirThe>M_PI/2) segm2DirThe=M_PI-segm2DirThe;
158 if(segm2DirPhi<0) segm2DirPhi+=2*M_PI;
159
160 // Vector Method
161 // Make vector between segment positions
162 //Trk::GlobalDirection segmVector;
163 Amg::Vector3D segmVector;
164
165 if(jMDT2>jMDT1)segmVector = segm2Pos-segm1Pos;
166 else segmVector = segm1Pos-segm2Pos;
167 float segmVecThe = segmVector.theta();
168 float segmVecPhi = segmVector.phi();
169 if(segmVecThe>M_PI/2) segmVecThe=M_PI-segmVecThe;
170 if(segmVecPhi<0) segmVecPhi+=2*M_PI;
171
172 // Get difference between vector direction and segment directions
173 float dThe_Vec_Segm1 = segmVecThe-segm1DirThe;
174 float dPhi_Vec_Segm1 = segmVecPhi-segm1DirPhi;
175 if(dPhi_Vec_Segm1<-M_PI)dPhi_Vec_Segm1+=2*M_PI;
176 if(dPhi_Vec_Segm1> M_PI)dPhi_Vec_Segm1-=2*M_PI;
177 float dThe_Vec_Segm2 = segmVecThe-segm2DirThe;
178 float dPhi_Vec_Segm2 = segmVecPhi-segm2DirPhi;
179 if(dPhi_Vec_Segm2<-M_PI)dPhi_Vec_Segm2+=2*M_PI;
180 if(dPhi_Vec_Segm2> M_PI)dPhi_Vec_Segm2-=2*M_PI;
181
182 // Fill histograms
183 if(jMDT1>jMDT2){
184 if(m_mdt_trackchecksag[i][jMDT2][jMDT1][2][0]) m_mdt_trackchecksag[i][jMDT2][jMDT1][2][0]->Fill(dPhi_Vec_Segm2);
185 if(m_mdt_trackchecksag[i][jMDT2][jMDT1][3][0]) m_mdt_trackchecksag[i][jMDT2][jMDT1][3][0]->Fill(dThe_Vec_Segm2);
186 if(m_mdt_trackchecksag[i][jMDT2][jMDT1][2][1]) m_mdt_trackchecksag[i][jMDT2][jMDT1][2][1]->Fill(dPhi_Vec_Segm1);
187 if(m_mdt_trackchecksag[i][jMDT2][jMDT1][3][1]) m_mdt_trackchecksag[i][jMDT2][jMDT1][3][1]->Fill(dThe_Vec_Segm1);
188 }
189 else if(jMDT1<jMDT2){
190 if(m_mdt_trackchecksag[i][jMDT1][jMDT2][2][0]) m_mdt_trackchecksag[i][jMDT1][jMDT2][2][0]->Fill(dPhi_Vec_Segm1);
191 if(m_mdt_trackchecksag[i][jMDT1][jMDT2][3][0]) m_mdt_trackchecksag[i][jMDT1][jMDT2][3][0]->Fill(dThe_Vec_Segm1);
192 if(m_mdt_trackchecksag[i][jMDT1][jMDT2][2][1]) m_mdt_trackchecksag[i][jMDT1][jMDT2][2][1]->Fill(dPhi_Vec_Segm2);
193 if(m_mdt_trackchecksag[i][jMDT1][jMDT2][3][1]) m_mdt_trackchecksag[i][jMDT1][jMDT2][3][1]->Fill(dThe_Vec_Segm2);
194 }
195
196 // Direction Comparison Method
197 float dTheDir_Segm1_Segm2 = segm1DirThe-segm2DirThe;
198 float dPhiDir_Segm1_Segm2 = segm1PosPhi-segm2PosPhi;
199 if(dPhiDir_Segm1_Segm2<-M_PI)dPhiDir_Segm1_Segm2+=2*M_PI;
200 if(dPhiDir_Segm1_Segm2> M_PI)dPhiDir_Segm1_Segm2-=2*M_PI;
201 if(m_mdt_trackdirdirsag[i][jMDT1][jMDT2][2]) m_mdt_trackdirdirsag[i][jMDT1][jMDT2][2]->Fill(dTheDir_Segm1_Segm2);
202 if(m_mdt_trackdirdirsag[i][jMDT1][jMDT2][3]) m_mdt_trackdirdirsag[i][jMDT1][jMDT2][3]->Fill(dPhiDir_Segm1_Segm2);
203 // Cut using Vector Method
204 if(dPhi_Vec_Segm1>dPhiCutSegmentDirectionChecking[jMDT1][jMDT2] ||
205 dThe_Vec_Segm1>dTheCutSegmentDirectionChecking[jMDT1][jMDT2] ||
206 dPhi_Vec_Segm2>dPhiCutSegmentDirectionChecking[jMDT2][jMDT1] ||
207 dThe_Vec_Segm2>dTheCutSegmentDirectionChecking[jMDT2][jMDT1]) continue;
208
209 // Match is found, increment counter and assign segm2 to match found array
210 matchingSegments[jMDT2].push_back(segm2);
211 }// nSegms2
212
213 if(matchingSegments[jMDT2].size()==1){
214 stationMatchFound[jMDT2]=true;
215 nStationMatch++;
216 }
217 }// Reverse MDT Stations2
218
219 // If matches found add to matchedSegments and disqualify all segments in array
220 if(nStationMatch>1){
221 //HasMatchedTrack=true;
222 const Muon::MuonSegment *segmArray[4] = {nullptr,nullptr,nullptr,nullptr};
223 for(int jMDT2=0;jMDT2<4;jMDT2++){
224 if(stationMatchFound[jMDT2]){
225 segmArray[jMDT2]=matchingSegments[jMDT2].at(0);
226 //HasStationMatchSegm[jMDT2]=true;
227 disqualifiedSegments[i][jMDT2].push_back(matchingSegments[jMDT2].at(0));
228 }
229 }
230 SegmTrack newTrack(segmArray);
231 matchedSegments[i].push_back(newTrack);
232 }// If Matched Track Found
233
234 }// nSegms1
235 }// Reverse MDT Stations1
236
237 }// AC
238
239 return;
240}// End of function
#define M_PI
size_t size() const
Number of registered mappings.
void MatchMDTSegments(std::vector< const Muon::MuonSegment * >(&sortedSegments)[2][4], std::vector< const Muon::MuonSegment * >(&disqualifiedSegments)[2][4], std::vector< SegmTrack >(&matchedSegments)[2])
TH1 * m_mdt_trackdirdirsag[2][4][4][4]
TH1 * m_mdt_segmmatchsag[2][4][4][4]
TH1 * m_mdt_trackchecksag[2][4][4][4][2]
This is the common class for 3D segments used in the muon spectrometer.
virtual const Amg::Vector3D & globalPosition() const override final
global position
Eigen::Matrix< double, 3, 1 > Vector3D