ATLAS Offline Software
Loading...
Searching...
No Matches
FPGATrackSimHoughFunctions.h File Reference
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Enumerations

enum class  ORAlgo { Normal , InvertGrouping }

Functions

long getVolumeID (const FPGATrackSimHit &hit)
long getCoarseID (const FPGATrackSimHit &hit)
long getFineID (const FPGATrackSimHit &hit)
bool isFineIDInStrip (long ID)
bool isFineIDInPixel (long ID)
void getMissingInfo (const FPGATrackSimRoad &road, int &nMissing, bool &missPixel, bool &missStrip, layer_bitmask_t &missing_mask, layer_bitmask_t &norecovery_mask, const ServiceHandle< IFPGATrackSimMappingSvc > &FPGATrackSimMapping, const TrackCorrType idealCoordFitType)
void makeTrackCandidates (const FPGATrackSimRoad &road, const FPGATrackSimTrack &temp, std::vector< FPGATrackSimTrack > &track_cands, const ServiceHandle< IFPGATrackSimMappingSvc > &FPGATrackSimMapping)
 Creates a list of track candidates by taking all possible combination of hits in road.
StatusCode runOverlapRemoval (std::vector< FPGATrackSimTrack > &tracks, const float minChi2, const int NumOfHitPerGrouping, ORAlgo orAlgo, ToolHandle< GenericMonitoringTool > &monTool, bool compareAllHits=false)
void findMinChi2MaxHit (const std::vector< int > &duplicates, std::vector< FPGATrackSimTrack > &RMtracks, std::vector< int > &flags_OR, const std::vector< int > &track_counter)
int findNonOverlapHits (const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
int findNCommonHits (const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
int findNCommonHitsGlobal (const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
void roadsToTrack (std::vector< FPGATrackSimRoad > &roads, std::vector< FPGATrackSimTrack > &track_cands, const FPGATrackSimPlaneMap *pmap)

Enumeration Type Documentation

◆ ORAlgo

enum class ORAlgo
strong
Enumerator
Normal 
InvertGrouping 

Definition at line 20 of file FPGATrackSimHoughFunctions.h.

Function Documentation

◆ findMinChi2MaxHit()

void findMinChi2MaxHit ( const std::vector< int > & duplicates,
std::vector< FPGATrackSimTrack > & RMtracks,
std::vector< int > & flags_OR,
const std::vector< int > & track_counter )

Definition at line 202 of file FPGATrackSimHoughFunctions.cxx.

203{
204 int dup_counter = 0;
205 int head_track = 1;
206 float head_chi2 = 0.;
207 int head_nhits = 0;
208
209 for(auto dup: duplicates)
210 {
211 float t_chi2 = RMtracks.at(dup).getChi2ndof();
212 int t_nhitlayers = RMtracks.at(dup).getFPGATrackSimHits().size();
213 for(auto& hit : RMtracks.at(dup).getFPGATrackSimHits())
214 {
215 ANA_MSG_DEBUG("Real hit info = " << hit);
216 ANA_MSG_DEBUG("Real hit info (global) = Gphi= " << hit.getGPhi() << " Z=" << hit.getZ() << " R=" << hit.getR() << " chi2=" << t_chi2);
217
218 if(!hit.isReal())
219 {
220 t_nhitlayers--;
221 }
222 }
223 if (dup_counter == 0) {
224 head_track = dup;
225 head_chi2 = RMtracks.at(head_track).getChi2ndof();
226 head_nhits = t_nhitlayers;
227 }
228 if (dup_counter > 0){
229 if(t_nhitlayers>head_nhits)
230 {
231 RMtracks.at(head_track).setPassedOR(0);
232 }
233 else if(t_nhitlayers==head_nhits)
234 {
235 if((head_chi2-t_chi2)>0.000001)
236 {
237 RMtracks.at(head_track).setPassedOR(0);
238 }
239 if(std::abs(t_chi2-head_chi2)<0.000001)
240 {
241 if(track_counter[head_track] < track_counter[dup]) {
242 RMtracks.at(dup).setPassedOR(0);
243 }
244 if(track_counter[head_track] > track_counter[dup]) {
245 RMtracks.at(head_track).setPassedOR(0);
246 }
247 }
248 }
249 }
250
251 if(!RMtracks.at(head_track).passedOR()) flags_OR[head_track] = 0;
252 if(RMtracks.at(head_track).passedOR()) flags_OR[head_track] = 1;
253 dup_counter++;
254
255 }
256}
#define ANA_MSG_DEBUG(xmsg)
Macro printing debug messages.

◆ findNCommonHits()

int findNCommonHits ( const FPGATrackSimTrack & Track1,
const FPGATrackSimTrack & Track2 )

Definition at line 353 of file FPGATrackSimHoughFunctions.cxx.

354{
355 int nCommHits=0;
356
357 // Loop through all layers
358 for(unsigned int i = 0; i < Track1.getFPGATrackSimHits().size(); ++i)
359 {
360 const FPGATrackSimHit& hit1 = Track1.getFPGATrackSimHits().at(i);
361 const FPGATrackSimHit& hit2 = Track2.getFPGATrackSimHits().at(i);
362
363 // Check if hit is missing
364 if(!hit1.isReal() || !hit2.isReal())
365 {
366 continue;
367 }
368 // Check if hit on the same plane
369 else if(hit1.getLayer() != hit2.getLayer())
370 {
371 continue;
372 }
373 // Check if two hits have the same hashID
374 else if(hit1.getIdentifierHash() != hit2.getIdentifierHash())
375 {
376 continue;
377 }
378 // Check if two hits have same coordinate. this is difficult due to spacepoints,
379 // since the same hit can be used to make multiple spacepoints.
380 else if (hit1.getHitType() == HitType::spacepoint && hit2.getHitType() == HitType::spacepoint) {
381
382 if ((std::abs(hit1.getX() - hit2.getX()) < EPSILON) && (std::abs(hit1.getY() - hit2.getY()) < EPSILON) && (std::abs(hit1.getZ() - hit2.getZ()) < EPSILON)) {
383 nCommHits++;
384 } else {
385 continue;
386 }
387 }
388 // If both hits aren't spacepoints, we should be able to do this comparison.
389 else if (std::abs(hit1.getGPhi()-hit2.getGPhi())<0.001 && std::abs(hit1.getZ()-hit2.getZ())<0.001 && std::abs(hit1.getR()-hit2.getR())<0.001) {
390 nCommHits++;
391 }
392 else
393 {
394 continue;
395 }
396 }
397 return nCommHits;
398}
constexpr float EPSILON
float getY() const
unsigned getIdentifierHash() const
float getX() const
float getGPhi() const
float getZ() const
float getR() const
bool isReal() const
HitType getHitType() const
const std::vector< FPGATrackSimHit > & getFPGATrackSimHits() const

◆ findNCommonHitsGlobal()

int findNCommonHitsGlobal ( const FPGATrackSimTrack & Track1,
const FPGATrackSimTrack & Track2 )

Definition at line 306 of file FPGATrackSimHoughFunctions.cxx.

307{
308 int nCommHits = 0;
309 std::vector<uint8_t> hit2_matched(Track2.getFPGATrackSimHits().size(), 0);
310
311 for (const auto& hit1 : Track1.getFPGATrackSimHits())
312 {
313 if (!hit1.isReal()) continue; // Skip if hit1 is not real
314
315 for (size_t j = 0; j < Track2.getFPGATrackSimHits().size(); ++j)
316 {
317 const auto& hit2 = Track2.getFPGATrackSimHits()[j];
318
319 if (hit2_matched[j]) continue; // already used this hit
320 else if (!hit2.isReal()) continue; // Check if hit is missing
321 else if (hit1.getLayer() != hit2.getLayer()) continue; // Check if hit on the same plane
322 else if (hit1.getIdentifierHash() != hit2.getIdentifierHash()) continue; // Check if two hits have the same hashID
323
324 // Check if two hits have same coordinate. this is difficult due to spacepoints,
325 // since the same hit can be used to make multiple spacepoints.
326 else if (hit1.getHitType() == HitType::spacepoint && hit2.getHitType() == HitType::spacepoint)
327 {
328 if (std::abs(hit1.getX() - hit2.getX()) < EPSILON &&
329 std::abs(hit1.getY() - hit2.getY()) < EPSILON &&
330 std::abs(hit1.getZ() - hit2.getZ()) < EPSILON)
331 {
332 nCommHits++;
333 hit2_matched[j] = true;
334 break;
335 }
336 }
337
338 // If both hits aren't spacepoints, we should be able to do this comparison.
339 else if (std::abs(hit1.getGPhi() - hit2.getGPhi()) < EPSILON &&
340 std::abs(hit1.getZ() - hit2.getZ()) < EPSILON &&
341 std::abs(hit1.getR() - hit2.getR()) < EPSILON)
342 {
343 nCommHits++;
344 hit2_matched[j] = true;
345 break;
346 }
347 }
348 }
349
350 return nCommHits;
351}

◆ findNonOverlapHits()

int findNonOverlapHits ( const FPGATrackSimTrack & Track1,
const FPGATrackSimTrack & Track2 )

Definition at line 156 of file FPGATrackSimHoughFunctions.cxx.

157{
158 int nonOverlapHits=0;
159
160 // Loop through all layers
161 for(unsigned int i = 0; i < Track1.getFPGATrackSimHits().size(); ++i)
162 {
163 const FPGATrackSimHit& hit1 = Track1.getFPGATrackSimHits().at(i);
164 const FPGATrackSimHit& hit2 = Track2.getFPGATrackSimHits().at(i);
165 // First make sure we are looking at real hits
166 if(!hit1.isReal() || !hit2.isReal())
167 {
168 continue;
169 }
170 // Check if two hits are on the same plane
171 else if(hit1.getLayer() != hit2.getLayer())
172 {
173 nonOverlapHits++;
174 }
175 // Check if two hits have the same hashID
176 else if(hit1.getIdentifierHash() != hit2.getIdentifierHash())
177 {
178 nonOverlapHits++;
179 }
180 // Check if two hits have same coordinate. this is difficult due to spacepoints,
181 // since the same hit can be used to make multiple spacepoints.
182 else if (hit1.getHitType() == HitType::spacepoint && hit2.getHitType() == HitType::spacepoint) {
183 if ((abs(hit1.getX() - hit2.getX()) > EPSILON) || (abs(hit1.getY() - hit2.getY()) > EPSILON) || (abs(hit1.getZ() - hit2.getZ()) > EPSILON)) {
184 nonOverlapHits++;
185 } else {
186 continue;
187 }
188 }
189 else if (std::abs(hit1.getGPhi()-hit2.getGPhi())>0.001 && std::abs(hit1.getZ()-hit2.getZ())>0.001 && std::abs(hit1.getR()-hit2.getR())>0.001)
190 {
191 nonOverlapHits++;
192 }
193 else
194 {
195 continue;
196 }
197 }
198 return nonOverlapHits;
199}

◆ getCoarseID()

long getCoarseID ( const FPGATrackSimHit & hit)

Definition at line 588 of file FPGATrackSimHoughFunctions.cxx.

589{
590 // Custom labelling for the detector layers
591 // to be used in NN training.
592 // This aims at providing a continuous numbering according to this convention:
593 // strip barrel layers in [0,3]
594 // strip C-side end cap layers in [4,9]
595 // strip A-side end cap layers in [10,15]
596 // pixel barrel layers in [16,20]
597 // pixel C-side end cap layers in [21,29]
598 // pixel A-side end cap layers > 30
599 // returns large negative value if no layer
600
601 long volumeID = getVolumeID(hit);
602 unsigned layerID = hit.getLayerDisk(true);
603
604 long offset = -10000;
605
606 if(volumeID == 10) offset = 0; //strip barrel
607 if(volumeID == 8) offset = 4; //strip -ve EC
608 if(volumeID == 12) offset = 10; //strip +ve EC
609 if(volumeID == 0) offset = 16; // pix barrel
610 if(volumeID == -2) offset = 21; //pix -ve EC
611 if(volumeID == 2) offset = 30; //pix +ve EC
612 return offset + layerID;
613}
long getVolumeID(const FPGATrackSimHit &hit)
unsigned getLayerDisk(bool old=false) const

◆ getFineID()

long getFineID ( const FPGATrackSimHit & hit)

Definition at line 625 of file FPGATrackSimHoughFunctions.cxx.

626{
627 // Custom labelling for the detector layers
628 // to be used in NN training.
629 // Returns a labelling of non-barrel pixel hits similar to a hit's eta index,
630 // but with a continuous numbering.
631 // Otherwise return convention defined in getCoarseID.
632
633 long volumeID = getVolumeID(hit);
634 unsigned layerID = hit.getLayerDisk(true);
635 int etaID = hit.getEtaModule(true);
636
637 long offset = -1000;
638
639 if(volumeID == 10) return getCoarseID(hit); //strip barrel
640 if(volumeID == 8) return getCoarseID(hit); //strip -ve EC
641 if(volumeID == 12) return getCoarseID(hit); //strip +ve EC
642 if(volumeID == 0) return getCoarseID(hit); //pix barrel
643 if(volumeID == -999) return -999; //hit not in any physical layer
644 if(volumeID == -2)
645 {
646 if(layerID == 0) offset = 21;
647 if(layerID == 1) offset = 21+15;
648 if(layerID == 2) offset = 21+15+6;
649 if(layerID == 3) offset = 21+15+6+23;
650 if(layerID == 4) offset = 21+15+6+23+6;
651 if(layerID == 5) offset = 21+15+6+23+6+11;
652 if(layerID == 6) offset = 21+15+6+23+6+11+8;
653 if(layerID == 7) offset = 21+15+6+23+6+11+8+8;
654 if(layerID == 8) offset = 21+15+6+23+6+11+8+8+9;
655 return offset + etaID;
656 }
657 if(volumeID == 2)
658 {
659 if(layerID == 0) offset = 116;
660 if(layerID == 1) offset = 116+15;
661 if(layerID == 2) offset = 116+15+6;
662 if(layerID == 3) offset = 116+15+6+23;
663 if(layerID == 4) offset = 116+15+6+23+6;
664 if(layerID == 5) offset = 116+15+6+23+6+11;
665 if(layerID == 6) offset = 116+15+6+23+6+11+8;
666 if(layerID == 7) offset = 116+15+6+23+6+11+8+8;
667 if(layerID == 8) offset = 116+15+6+23+6+11+8+8+9;
668 return offset + etaID;
669 }
670
671 return -1;
672}
long getCoarseID(const FPGATrackSimHit &hit)
int getEtaModule(bool old=false) const

◆ getMissingInfo()

void getMissingInfo ( const FPGATrackSimRoad & road,
int & nMissing,
bool & missPixel,
bool & missStrip,
layer_bitmask_t & missing_mask,
layer_bitmask_t & norecovery_mask,
const ServiceHandle< IFPGATrackSimMappingSvc > & FPGATrackSimMapping,
const TrackCorrType idealCoordFitType )

Definition at line 402 of file FPGATrackSimHoughFunctions.cxx.

403{
404 int subregion = road.getSubRegion();
405 nMissing = FPGATrackSimMapping->PlaneMap_1st(subregion)->getNCoords(); // init with nCoords and decrement as we find misses
406 missPixel = false;
407 missStrip = false;
408 missing_mask = 0;
409 norecovery_mask = 0;
410 unsigned int wclayers = road.getWCLayers();
411 for (unsigned layer = 0; layer < FPGATrackSimMapping->PlaneMap_1st(subregion)->getNLogiLayers(); layer++)
412 {
413 int nHits = road.getHits(layer).size();
414 if (nHits==0)
415 {
416 if (idealCoordFitType == TrackCorrType::None && ((wclayers >> layer) & 1))
417 {
418 int ix = FPGATrackSimMapping->PlaneMap_1st(subregion)->getCoordOffset(layer);
419 int iy = ix + 1;
420 if (FPGATrackSimMapping->PlaneMap_1st(subregion)->isSCT(layer))
421 {
422 missing_mask |= 1 << ix;
423 nMissing -= 1;
424 }
425 else
426 {
427 missing_mask |= (1<<ix) | (1<<iy);
428 nMissing -= 2;
429 }
430 }
431 else
432 {
433 if (FPGATrackSimMapping->PlaneMap_1st(subregion)->isSCT(layer)) missStrip = true;
434 else missPixel = true;
435 }
436 }
437 else if (!((wclayers >> layer) & 1)) { // we have a hit
438 int ix = FPGATrackSimMapping->PlaneMap_1st(subregion)->getCoordOffset(layer);
439 int iy = ix + 1;
440 if (FPGATrackSimMapping->PlaneMap_1st(subregion)->isSCT(layer))
441 {
442 missing_mask |= 1 << ix;
443 nMissing -= 1;
444 }
445 else
446 {
447 missing_mask |= (1<<ix) | (1<<iy);
448 nMissing -= 2;
449 }
450
451 }
452 }
453}
static const uint32_t nHits
const std::vector< std::shared_ptr< const FPGATrackSimHit > > & getHits(size_t layer) const
int getSubRegion() const
layer_bitmask_t getWCLayers() const
@ layer
Definition HitInfo.h:79

◆ getVolumeID()

long getVolumeID ( const FPGATrackSimHit & hit)

Definition at line 533 of file FPGATrackSimHoughFunctions.cxx.

534{
535 // Custom labelling for the detector volumes
536 // to be used in NN training.
537 // Convention:
538 // barrel | else
539 //-------------------------------------
540 // Pixel | 0 | 2*sign(z)
541 // Strip | 10 | 10 + 2*sign(z)
542 //
543 // Explicitly:
544 // -2: C-side (-z) end cap pixel
545 // 0: barrel pixel
546 // 2: A-side (+z) end cap pixel
547 // 8: C-side end cap strip
548 // 10: barrel strip
549 // 12: A-sde end cap strip
550 // returns -999 if not a real hit
551
552
553 long volumeID = -1;
554
555 if (hit.getR() == 0.0) {
556 return -999; //hit not in any physical layer
557 }
558
559 if(hit.isBarrel()) {
560 if (hit.isPixel()) {
561 volumeID = 0;
562 }
563 if (hit.isStrip()) {
564 volumeID = 10;
565 }
566 }
567 else {
568 if (hit.isPixel()) {
569 if (hit.getZ() >= 0.) {
570 volumeID = 2;
571 }
572 else {
573 volumeID = -2;
574 }
575 }
576 else if (hit.isStrip()) {
577 if (hit.getZ() >= 0.) {
578 volumeID = 12;
579 }
580 else {
581 volumeID = 8;
582 }
583 }
584 }
585 return volumeID;
586}
bool isBarrel() const
bool isPixel() const
bool isStrip() const

◆ isFineIDInPixel()

bool isFineIDInPixel ( long ID)

Definition at line 620 of file FPGATrackSimHoughFunctions.cxx.

621{
622 return !isFineIDInStrip(ID);
623}
std::vector< Identifier > ID
bool isFineIDInStrip(long ID)

◆ isFineIDInStrip()

bool isFineIDInStrip ( long ID)

Definition at line 615 of file FPGATrackSimHoughFunctions.cxx.

616{
617 return (ID < 16);
618}

◆ makeTrackCandidates()

void makeTrackCandidates ( const FPGATrackSimRoad & road,
const FPGATrackSimTrack & temp,
std::vector< FPGATrackSimTrack > & track_cands,
const ServiceHandle< IFPGATrackSimMappingSvc > & FPGATrackSimMapping )

Creates a list of track candidates by taking all possible combination of hits in road.

Sets basic ID info and hits.

NB: If the number of combinations becomes large and memory is a concern, it may be worth turning this function into a sort of iterator over combs, return a single track each call.

Definition at line 464 of file FPGATrackSimHoughFunctions.cxx.

465{
466 int idbase = 0; // offset for new track ids
467 int subregion = road.getSubRegion();
468 auto pmap = FPGATrackSimMapping->PlaneMap_2nd(subregion);
469
470 if (temp.getTrackStage() == TrackStage::FIRST) {
471 pmap = FPGATrackSimMapping->PlaneMap_1st(subregion);
472 }
473
474 std::vector<std::vector<int>> combs = ::getComboIndices(road.getNHits_layer());
475 track_cands.resize(combs.size(), temp);
476
477 const FPGATrackSimRegionMap* SUBREGIONMAP = FPGATrackSimMapping->SubRegionMap_2nd();
478 //
479 //get the WC hits:
480 layer_bitmask_t wcbits= road.getWCLayers();
481 // Add the hits from each combination to the track, and set ID
482 for (size_t icomb = 0; icomb < combs.size(); icomb++)
483 {
484 //Need to set the ID and the hits size of this track
485 track_cands[icomb].setTrackID(idbase + icomb);
486 track_cands[icomb].setNLayers(pmap->getNLogiLayers());
487
488 // If this is an idealized coordinate fit; keep references to the idealized radii.
489 track_cands[icomb].setIdealRadii(SUBREGIONMAP->getAvgRadii(subregion));
490 track_cands[icomb].setPassedOR(1);
491
492 std::vector<int> const & hit_indices = combs[icomb]; // size nLayers
493 for (unsigned layer = 0; layer < pmap->getNLogiLayers(); layer++)
494 {
495 if (hit_indices[layer] < 0) // Set a dummy hit if road has no hits in this layer
496 {
498 newhit.setLayer(layer);
499 newhit.setSection(0);
500 if (pmap->getDim(layer) == 2) newhit.setDetType(SiliconTech::pixel);
501 else newhit.setDetType(SiliconTech::strip);
502
503 if (wcbits & (1 << layer ) ) {
505 newhit.setLayer(layer);
506 }
507
508 track_cands[icomb].setFPGATrackSimHit(layer, newhit);
509 }
510 else
511 {
512 const std::shared_ptr<const FPGATrackSimHit> hit = road.getHits(layer)[hit_indices[layer]];
513 // If this is an outer spacepoint, and it is not the same as the inner spacepoint, reject it.
514 // Here we "reject" it by marking the candidate as "invalid", to be rejected later.
515 // That require another field on the track object, but it avoids having to change the sizes
516 // of arrays computed above.
517 if (hit->getHitType() == HitType::spacepoint && (hit->getPhysLayer(true) % 2) == 1) {
518 if (layer == 0) throw (std::out_of_range("makeTrackCandidates: Attempt to access vector at element -1"));
519 const FPGATrackSimHit & inner_hit = track_cands[icomb].getFPGATrackSimHits().at(layer - 1);
520 if ((abs(hit->getX() - inner_hit.getX()) > EPSILON) || (abs(hit->getY() - inner_hit.getY()) > EPSILON) || (abs(hit->getZ() - inner_hit.getZ()) > EPSILON)) {
521 track_cands[icomb].setValidCand(false);
522 }
523 }
524 track_cands[icomb].setFPGATrackSimHit(layer, *hit);
525 }
526 }
527 }
528
529 idbase += combs.size();
530}
std::vector< std::vector< int > > getComboIndices(std::vector< size_t > const &sizes)
Given a vector of sizes (of arrays), generates a vector of all combinations of indices to index one e...
uint32_t layer_bitmask_t
void setLayer(unsigned v)
void setHitType(HitType type)
void setSection(unsigned v)
void setDetType(SiliconTech detType)
const std::vector< double > & getAvgRadii(unsigned region) const
std::vector< size_t > getNHits_layer() const

◆ roadsToTrack()

void roadsToTrack ( std::vector< FPGATrackSimRoad > & roads,
std::vector< FPGATrackSimTrack > & track_cands,
const FPGATrackSimPlaneMap * pmap )

Definition at line 675 of file FPGATrackSimHoughFunctions.cxx.

676{
677
678
679 for (const FPGATrackSimRoad& road : roads) {
680
682 temp.setNLayers(pmap->getNLogiLayers());
683 temp.setBankID(-1);
684 temp.setPatternID(road.getPID());
685 temp.setHoughX(road.getX());
686 temp.setHoughY(road.getY());
687 temp.setQOverPt(road.getY());
688
689 temp.setSubRegion(road.getSubRegion());
690 temp.setHoughXBin(road.getXBin());
691 temp.setHoughYBin(road.getYBin());
692 temp.setChi2(0);
693
694 temp.setBinIdx(road.getBinIdx());
695
696 // This comes from FPGATrackSimFunctions
697 std::vector<std::vector<int>> combs = getComboIndices(road.getNHits_layer());
698 unsigned existing_size = track_cands.size();
699 track_cands.resize(existing_size + combs.size(), temp);
700
701 //get the WC hits:
702 layer_bitmask_t wcbits= road.getWCLayers();
703 // Add the hits from each combination to the track, and set ID
704 for (size_t icomb = 0; icomb < combs.size(); icomb++)
705 {
706 if ((existing_size + icomb) >= track_cands.size()) continue;
707 track_cands[existing_size + icomb].setNLayers(pmap->getNLogiLayers());
708 std::vector<int> const & hit_indices = combs[icomb]; // size nLayers
709 for (unsigned layer = 0; layer < pmap->getNLogiLayers(); layer++)
710 {
711 if (hit_indices[layer] < 0) // Set a dummy hit if road has no hits in this layer
712 {
714 newhit.setLayer(layer);
715 newhit.setSection(0);
716 if (pmap->getDim(layer) == 2) newhit.setDetType(SiliconTech::pixel);
717 else newhit.setDetType(SiliconTech::strip);
718
719 if (wcbits & (1 << layer ) ) {
721 newhit.setLayer(layer);
722 }
723
724 track_cands[existing_size + icomb].setFPGATrackSimHit(layer, newhit);
725 }
726 else
727 {
728 const std::shared_ptr<const FPGATrackSimHit> hit = road.getHits(layer)[hit_indices[layer]];
729 // If this is an outer spacepoint, and it is not the same as the inner spacepoint, reject it.
730 // Here we "reject" it by marking the candidate as "invalid", to be rejected later.
731 // That require another field on the track object, but it avoids having to change the sizes
732 // of arrays computed above.
733 if (hit->getHitType() == HitType::spacepoint && (hit->getPhysLayer() % 2) == 1 && (layer>0)) {
734 const FPGATrackSimHit inner_hit = track_cands[existing_size + icomb].getFPGATrackSimHits().at(layer - 1);
735 if ((hit->getX() != inner_hit.getX()) || (hit->getY() != inner_hit.getY()) || (hit->getZ() != inner_hit.getZ())) {
736 track_cands[existing_size + icomb].setValidCand(false);
737 }
738 }
739 track_cands[existing_size + icomb].setFPGATrackSimHit(layer, *hit);
740 }
741 }
742 }
743 }
744}
uint32_t getNLogiLayers() const
uint32_t getDim(size_t logiLayer) const
void setNLayers(int)
set the number of layers in the track.

◆ runOverlapRemoval()

StatusCode runOverlapRemoval ( std::vector< FPGATrackSimTrack > & tracks,
const float minChi2,
const int NumOfHitPerGrouping,
ORAlgo orAlgo,
ToolHandle< GenericMonitoringTool > & monTool,
bool compareAllHits = false )

Definition at line 15 of file FPGATrackSimHoughFunctions.cxx.

16{
17 ANA_MSG_DEBUG("Beginning runOverlapRemoval()");
18 ANA_MSG_DEBUG("Tracks in event: " << tracks.size());
19
20 std::vector<int> flags_OR;
21 flags_OR.clear();
22
23 // Debug variables
24 int ntrack_passOR = 0;
25 int ntrack = 0;
26 std::vector<int> track_passOR_counter(tracks.size(), -1);
27 std::vector<int> track_passOR_barcodefrac(tracks.size(), -1);
28 int ntrack_passOR_total = 0;
29 int trackMuon_gt0pt5_passOR = 0;
30 float tmp_TrueTrack_BCF = -999;
31
32 // Pre-filter tracks with bad chi2
33 std::vector<unsigned int> goodTrackIndices;
34 goodTrackIndices.reserve(tracks.size());
35 for(unsigned int i = 0; i < tracks.size(); i++)
36 {
37 if(tracks[i].getChi2ndof() > minChi2)
38 {
39 tracks[i].setPassedOR(0);
40 }
41 else
42 {
43 goodTrackIndices.push_back(i);
44 }
45 }
46
47 // Pre-compute track_counter based on chi2 cuts (static per event, doesn't depend on track pairs)
48 std::vector<int> track_counter;
49 int ntr_belowMinChi2 = 0;
50 for(unsigned int i=0; i<tracks.size();i++)
51 {
52 if(tracks.at(i).getChi2ndof() > minChi2) {
53 track_counter.push_back(0);
54 flags_OR.push_back(-1);
55 } else {
56 ntr_belowMinChi2++;
57 track_counter.push_back(ntr_belowMinChi2);
58 flags_OR.push_back(1);
59 }
60 }
61
62 // Create tracks to hold and compare - only process good tracks
63 for(size_t idx = 0; idx < goodTrackIndices.size(); idx++)
64 {
65 unsigned int i = goodTrackIndices[idx];
66 FPGATrackSimTrack &fit1 = tracks.at(i);
67
68 // Skip if already marked as failed
69 if(!fit1.passedOR()) continue;
70
71 // Create vector for holding duplicate track list
72 std::vector<int> duplicates(1,i);
73
74 // Loop through ALL other good tracks (not just those after)
75 for(size_t jdx = 0; jdx < goodTrackIndices.size(); jdx++)
76 {
77 if(jdx == idx) continue; // Skip comparing with itself
78
79 unsigned int j = goodTrackIndices[jdx];
80 FPGATrackSimTrack &fit2 = tracks.at(j);
81
82 // Based on the algorithm choose common hit of non-common hit
83 if(orAlgo == ORAlgo::Normal)
84 {
85 // Find the number of common hits between two tracks. We have two ways to do this:
86 // * only compare hits in the same 'layer', requires tracks to be the same size.
87 // * compare every hit to every other hit; allows for tracks to be different sizes.
88 int nOverlappingHits = 0;
89 nOverlappingHits = (compareAllHits) ? findNCommonHitsGlobal(fit1, fit2) : findNCommonHits(fit1, fit2);
90
91 // Group overlapping tracks into a vector for removal if at least [NumOfHitPerGrouping] hits are the same
92 if(nOverlappingHits >= NumOfHitPerGrouping)
93 {
94 duplicates.push_back(j);
95 }
96 }
97 else if(orAlgo == ORAlgo::InvertGrouping)
98 {
99 // Find the number of non-common hits between two tracks using coordinate comparison
100 int nNotOverlappingHits = 0;
101 nNotOverlappingHits = findNonOverlapHits(fit1, fit2);
102
103 // If the number of non-overlapping hit is [NumOfHitPerGrouping] or less
104 if(nNotOverlappingHits <= NumOfHitPerGrouping)
105 {
106 duplicates.push_back(j);
107 }
108 }
109 }
110 findMinChi2MaxHit(duplicates, tracks, flags_OR, track_counter);
111
112
113 // Monitoring
114 ntrack++;
115 track_passOR_counter[i] = ntrack;
116 // barcodeFrac should be set in the track upstream e.g in FPGATrackSimLogicalHitsProcessAlg.cxx using calculateTruth()
117 if (fit1.getBarcodeFrac() < 0)
118 ANA_MSG_WARNING("barcodeFrac not set!");
119 track_passOR_barcodefrac[i] = fit1.getBarcodeFrac();
120 // check if the track passes OR and has barcodeFrac > 0.5
121 if(fit1.getBarcodeFrac() > 0.5 && fit1.passedOR()) {
122 // count how many muon tracks satisfy the condition
123 trackMuon_gt0pt5_passOR++;
124 // for the first passing track, record its barcodeFrac
125 if(trackMuon_gt0pt5_passOR == 1) {
126 tmp_TrueTrack_BCF = fit1.getBarcodeFrac();
127 }
128 // for subsequent passing tracks, keep the largest barcodeFrac
129 else if (fit1.getBarcodeFrac() > tmp_TrueTrack_BCF) {
130 tmp_TrueTrack_BCF = fit1.getBarcodeFrac();
131 }
132 }
133
134 }
135
136 // Monitoring histograms
137 ANA_MSG_DEBUG("List of tracks passing OR:: ");
138 for(unsigned int i=0; i<tracks.size();i++){
139 FPGATrackSimTrack &fit1 = tracks.at(i);
140 if(fit1.passedOR()) {
141 ntrack_passOR++;
142 ANA_MSG_DEBUG("track# = " << track_passOR_counter[i] << ": chi2 = " << fit1.getChi2ndof() << " barcodefrac = " << track_passOR_barcodefrac[i]);
143 }
144 }
145 ntrack_passOR_total += ntrack_passOR;
146 auto mon_ntrack_passOR = Monitored::Scalar<int>("ntrack_passOR", ntrack_passOR);
147 auto mon_barcodeFrac_passOR = Monitored::Scalar<int>("barcodeFrac_passOR", tmp_TrueTrack_BCF);
148 Monitored::Group(monTool, mon_ntrack_passOR);
149 Monitored::Group(monTool, mon_barcodeFrac_passOR);
150 ANA_MSG_DEBUG("Number of tracks passing OR (total) = " << ntrack_passOR_total);
151
152
153 return StatusCode::SUCCESS;
154}
#define ANA_MSG_WARNING(xmsg)
Macro printing warning messages.
void findMinChi2MaxHit(const std::vector< int > &duplicates, std::vector< FPGATrackSimTrack > &RMtracks, std::vector< int > &flags_OR, const std::vector< int > &track_counter)
int findNonOverlapHits(const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
int findNCommonHitsGlobal(const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
int findNCommonHits(const FPGATrackSimTrack &Track1, const FPGATrackSimTrack &Track2)
float getBarcodeFrac() const
unsigned int passedOR() const
float getChi2ndof() const
Group of local monitoring quantities and retain correlation when filling histograms
Declare a monitored scalar variable.