66{
67
68 bool TrkCouldBeAccepted = true;
69
70
75 bool thishasblayer = false;
76 bool hassharedblayer = false;
77 bool hassharedpixel = false;
78 bool firstisshared = true;
79
80
81 const Trk::RIO_OnTrack* lastrot = nullptr;
82 const Trk::RIO_OnTrack* lastbutonerot = nullptr;
83 int lastrotindex = 0;
84
85
88 const DataVector<const Trk::TrackParameters>* vpar = ptrTrack->trackParameters();
90
92 if (expected > nCutTRT) nCutTRT = expected;
93 }
94
95
97 ATH_MSG_DEBUG (
"Study new Track "<< ptrTrack<<
"\t , it has "<<tsos->
size()<<
"\t track states");
98 ATH_MSG_DEBUG (
"trackId "<< trackId <<
", subtrackId "<<subtrackId);
99
100
102 if (ispatterntrack) {
103 ATH_MSG_DEBUG (
"==> this is a pattern track, outliers are good hits (reintegration) !");
104 } else {
105 ATH_MSG_DEBUG (
"==> this is a refitted track, so we can use the chi2 ! ");
106 }
107
108
109 int nPixelDeadSensor = -1;
110 int nSCTDeadSensor = -1;
111 int npixel = 0;
112 int npixholes = 0;
113 int nsctholes = 0;
114 const Trk::TrackSummary* trkSummary=ptrTrack->trackSummary();
115 if (trkSummary) {
122 }
123
124
125 if (nPixelDeadSensor == -1) nPixelDeadSensor = 0;
126 if (nSCTDeadSensor == -1) nSCTDeadSensor = 0;
127 ATH_MSG_VERBOSE (
"---> Number of dead si sensors: " << nPixelDeadSensor + nSCTDeadSensor);
128
129
130 enum TsosTypes {
131
132 UnusedHit = 1,
133
134 SharedHit = 2,
135
136 RejectedHit = 3,
137
139
140 OtherTsos = 5
141 };
142
143 std::vector<int> tsosType;
144 tsosType.resize(tsos->
size());
145
146
149 for (
int index = 0 ; iTsos != iTsosEnd ; ++iTsos, ++
index) {
150
151
152 tsosType[
index] = OtherTsos;
153
154
155 const Trk::MeasurementBase* meas = (*iTsos)->measurementOnTrack();
156
157
158 if (!meas) {
159 ATH_MSG_VERBOSE (
"-> No measurement on TSOS, it is another type, to be copied over");
160 tsosType[
index] = OtherTsos;
161 continue;
162 }
163
164
165 const Trk::RIO_OnTrack* rot = dynamic_cast <const Trk::RIO_OnTrack*> (meas);
166 if (!rot) {
167
168 const Trk::PseudoMeasurementOnTrack* pseudo = dynamic_cast <const Trk::PseudoMeasurementOnTrack*> (meas);
169 if (pseudo){
171 } else {
172 ATH_MSG_WARNING (
"-> Measurement is not a pseudo measurment, not yet supported, try to copy !");
173 }
174 tsosType[
index] = OtherTsos;
175 continue;
176 }
177
178
179
180
181
182
183 const Identifier&
id = rot->
identify();
184 bool isTRT =
m_detID->is_trt(
id);
185 bool isPixel =
m_detID->is_pixel(
id);
186 bool isBlayer = isPixel ?
m_detID->is_blayer(
id) :
false;
188
189
190 if (isBlayer && (!isoutlier || ispatterntrack)) thishasblayer = true;
191
192
193 if ( isPixel && !thishasblayer && npixholes>0 &&
194 ( ( npixel==1 && !isoutlier ) ||
195 ( ispatterntrack && npixel==0 && isoutlier) ) ) {
196 ATH_MSG_VERBOSE (
"-> Special case, problematic single pixel hit on track, reject it !");
197 tsosType[
index] = RejectedHit;
198
199 TrkCouldBeAccepted = false;
200 continue;
201 }
202
203
204
205 if ( (isoutlier && !ispatterntrack) || !(
m_detID->is_indet(
id)) ) {
206 ATH_MSG_VERBOSE (
"-> Prd is outlier on a fitter track (or not InDet), copy it over");
208 continue;
209 }
210
211
213 if ( !isoutlier ) {
215 } else {
216 ATH_MSG_VERBOSE (
"-> Prd is outlier on a pattern track and is unused, copy it over");
217 }
218
219 tsosType[
index] = UnusedHit;
220
223
224 if (numShared == 0) firstisshared = false;
225
226 lastbutonerot = lastrot;
227 lastrot = rot;
228 lastrotindex =
index;
229
230 continue;
231 }
232
233
234
235
236
237
238 if ( isoutlier && ispatterntrack ) {
239 ATH_MSG_VERBOSE (
"-> Shared Prd is outlier on a pattern track, we do not want to reintegrate it, so reject it ");
240 tsosType[
index] = RejectedHit;
241
242 TrkCouldBeAccepted = false;
243 continue;
244 }
245
246
247 if (isTRT) {
249 tsosType[
index] = RejectedHit;
250
251 TrkCouldBeAccepted = false;
252 continue;
253 }
254
255
256
257
258
260 int numberOfTracksWithThisPrd = std::distance(
range.first,
range.second);
262
263
266 (!isPixel || npixholes<=0) ) {
267
268
270
271 const InDet::PixelCluster* clus =
dynamic_cast <const InDet::PixelCluster*
> (rot->
prepRawData());
272
273 if ( !clus ) {
274 ATH_MSG_WARNING (
"-----> cast to Pixel cluster failed, should not happen !");
275
276 TrkCouldBeAccepted = false;
277 continue;
278 } else {
279
280
281 const Trk::ClusterSplitProbabilityContainer::ProbabilityInfo &splitProb = splitProbContainer.
splitProbability(clus);
283 ATH_MSG_VERBOSE (
"-----> Pixel cluster is split, reject shared hit !!!");
284 tsosType[
index] = RejectedHit;
285
286 TrkCouldBeAccepted = false;
287 continue;
288 }
289
290
291
292
294 ATH_MSG_VERBOSE (
"-----> Pixel cluster is not compatible with being shared (splitProb = "
296 tsosType[
index] = RejectedHit;
297
298 TrkCouldBeAccepted = false;
299 continue;
300 }
301 }
302 }
303
304 ATH_MSG_VERBOSE (
"---> Shared hit, but good track, let's enter hit in the list and try to keep it !");
305 tsosType[
index] = SharedHit;
308
309
310 if (isPixel) {
311
312 if (isBlayer) hassharedblayer = true;
313 else hassharedpixel = true;
314 }
315
316 lastbutonerot = lastrot;
317 lastrot = rot;
318 lastrotindex =
index;
319
320 continue;
321 }
322
323
325 tsosType[
index] = RejectedHit;
326
327 TrkCouldBeAccepted = false;
328 }
329
330
332
333
334 if (ispatterntrack &&
336 (lastrot && lastbutonerot) &&
338 ATH_MSG_DEBUG (
"Special cut on distance, reject last hit on track !");
339 tsosType[lastrotindex] = RejectedHit;
341
342 TrkCouldBeAccepted = false;
343 }
344
345
346 if (ispatterntrack &&
348 nsctholes>3 ) {
349 ATH_MSG_DEBUG (
"Special cut on too many holes, reject last hit on track !");
350 tsosType[lastrotindex] = RejectedHit;
352
353 TrkCouldBeAccepted = false;
354 }
355
356
357
358
359 if ( !ispatterntrack ) {
360 double trackchi2 = 0.;
361 if (ptrTrack->fitQuality() && ptrTrack->fitQuality()->numberDoF()>0 )
362 trackchi2 = ptrTrack->fitQuality()->chiSquared()/ptrTrack->fitQuality()->numberDoF();
363
364
365 if ( numShared > 0 && !ispatterntrack && trackchi2 > 3 ) {
366 ATH_MSG_DEBUG (
"Shared hits, we have a bad chi2 track, mark it as bad !");
367
368 TrkCouldBeAccepted = false;
369 }
370 }
371
372
373
374 if ( numTRT_Unused < nCutTRT) {
376
377 TrkCouldBeAccepted = false;
378 }
379
380
381
382
383
384
385 if ( TrkCouldBeAccepted &&
386 ( !hassharedblayer || npixholes<=1 ) &&
387 !hassharedpixel &&
388 ( ( totalSiHits >=
m_minHits && numShared == 0 ) ||
391 ATH_MSG_DEBUG (
"=> Suggest to keep track with "<<numShared<<
" shared hits !");
392 return std::make_tuple(static_cast<Trk::Track *>(nullptr),true);
393
394
395 } else if ( numTRT_Unused >= nCutTRT &&
399
401 ATH_MSG_DEBUG (
"=> Cosmics, accept input track even with shared hits");
402 return std::make_tuple(static_cast<Trk::Track *>(nullptr),true);
403 }
404
405
406
407
408
409
410
411
412
413 ATH_MSG_VERBOSE (
"Trying to recover track, allow for some shared hits is possible.");
414
415
416 std::vector<const Trk::TrackStateOnSurface*> newTSOS;
417
418
419 int cntIns = 0;
420
421
424
425 for (
int index = 0 ; iTsos != iTsosEnd ; ++iTsos,++
index ) {
426
427
428 if (tsosType[index] == RejectedHit) {
430
431 } else if (tsosType[index] != SharedHit ) {
433 newTSOS.push_back(*iTsos);
434
437
438 } else {
440
441
442 const Trk::MeasurementBase* meas = (*iTsos)->measurementOnTrack();
443
444 const Trk::RIO_OnTrack* rot = dynamic_cast <const Trk::RIO_OnTrack*> (meas);
445
446 if (!rot) {
448 continue;
449 }
450
451
453
454
456 int numberOfTracksWithThisPrd = std::distance(
range.first,
range.second);
458
459
460 int iShared = 0;
461 int othernpixel = 0;
462 bool otherhasblayer = false;
463 if ( numberOfTracksWithThisPrd == 1 ) {
464
465 std::vector< const Trk::PrepRawData* > prdsToCheck =
m_assoTool->getPrdsOnTrack(prd_to_track_map,*(
range.first->second));
466 for (const Trk::PrepRawData* prd : prdsToCheck) {
467 if (prd_to_track_map.
isShared(*prd))
468 ++iShared;
469 if (
m_detID->is_pixel(prd->identify())) {
470 othernpixel++;
471 if (
m_detID->is_blayer(prd->identify())) otherhasblayer=
true;
472 }
473 }
474 }
475
476
479 (!isPixel || !hassharedblayer || npixholes <= 0) &&
480 ( iShared <
m_maxShared || (isPixel && !firstisshared) ) &&
481 (!isPixel || thishasblayer == otherhasblayer ) &&
482 (!isPixel || npixel >= othernpixel ) ) {
483
484 ATH_MSG_VERBOSE (
"---> Accepted hit shared with " << numberOfTracksWithThisPrd <<
" tracks !");
485 newTSOS.push_back(*iTsos);
487
488
489 cntIns += (isPixel ? 2 : 1);
490
491 } else {
492 ATH_MSG_VERBOSE (
"---> Reject hit shared with " << numberOfTracksWithThisPrd <<
" tracks !");
493 }
494 }
495 }
496
497
498 if ( numUnused+nPixelDeadSensor+nSCTDeadSensor <
m_minHits || newTSOS.size() <= 3 ) {
499 ATH_MSG_DEBUG (
"=> Too few hits, reject track with shared hits");
500 return std::make_tuple(static_cast<Trk::Track *>(nullptr),false);
501 }
502
503
504 if ( newTSOS.size() == tsos->
size() ) {
506 return std::make_tuple(static_cast<Trk::Track *>(nullptr),true);
507 } else {
508
510 if (!newTrack) {
512 return std::make_tuple(static_cast<Trk::Track *>(nullptr),false);
513 }
514
516 info.addPatternRecoAndProperties(ptrTrack->info());
517 Trk::TrackInfo newInfo;
519 info.addPatternReco(newInfo);
521
522 ATH_MSG_DEBUG (
"=> Successfully created subtrack with shared hits recovered !");
523 return std::make_tuple(newTrack,false);
524 }
525 } else {
527 }
528
529 return std::make_tuple(static_cast<Trk::Track *>(nullptr),false);
530}
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
DataModel_detail::const_iterator< DataVector > const_iterator
const_iterator end() const noexcept
Return a const_iterator pointing past the end of the collection.
const_iterator begin() const noexcept
Return a const_iterator pointing at the beginning of the collection.
size_type size() const noexcept
Returns the number of elements in the collection.
const ProbabilityInfo & splitProbability(const PrepRawData *cluster) const
bool isUsed(const PrepRawData &prd) const
does this PRD belong to at least one track?
PrepRawDataTrackMapRange onTracks(const PrepRawData &prd)
get the Tracks associated with this PrepRawData.
std::pair< PrepRawDataTrackMap::const_iterator, PrepRawDataTrackMap::const_iterator > ConstPrepRawDataTrackMapRange
bool isShared(const PrepRawData &prd) const
does this PRD belong to more than one track?
const std::vector< Identifier > & rdoList() const
return the List of rdo identifiers (pointers)
virtual const Trk::PrepRawData * prepRawData() const =0
returns the PrepRawData (also known as RIO) object to which this RIO_OnTrack is associated.
Identifier identify() const
return the identifier -extends MeasurementBase
virtual const Amg::Vector3D & globalPosition() const override=0
Interface method to get the global Position.
@ Unknown
Track fitter not defined.
void addPatternReco(const TrackInfo &)
A method adding just pattern recognition info without adding the actual properties.
@ Outlier
This TSoS contains an outlier, that is, it contains a MeasurementBase/RIO_OnTrack which was not used ...
int get(const SummaryType &type) const
returns the summary information for the passed SummaryType.
const TrackInfo & info() const
Returns a const ref to info of a const tracks.
DataVector< const Trk::TrackStateOnSurface > TrackStates
ParametersBase< TrackParametersDim, Charged > TrackParameters
@ numberOfPixelHits
number of pixel layers on track with absence of hits
@ numberOfSCTHoles
number of Holes in both sides of a SCT module
@ numberOfSCTDeadSensors
number of TRT hits
@ numberOfPixelHoles
number of pixels which have a ganged ambiguity.
@ numberOfPixelDeadSensors
number of pixel hits with broad errors (width/sqrt(12))
float splitProbability1() const