24 (
const std::string&
t,
const std::string&
n,
const IInterface*
p)
27 declareInterface<ITRT_TrackSegmentsMaker>(
this);
32 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::initialize(), March 2012"
43 return StatusCode::FAILURE;
53 if (m_minSeedTOT<0. || m_minSeedTOT>20.)
56 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::initialize(), jobProperties: "
64 return StatusCode::SUCCESS;
73 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::newEvent()");
78 if (not trtcontainer.
isValid()) {
79 msg(MSG::ERROR) <<
"Could not find TRT_DriftCircles collection!" <<
endmsg;
80 std::stringstream
msg;
82 throw std::runtime_error(
msg.str());
85 std::unique_ptr<TRT_TrackSegmentsMaker_BarrelCosmics::EventData>
86 event_data = std::make_unique<TRT_TrackSegmentsMaker_BarrelCosmics::EventData>(trtcontainer.
cptr());
88 for(
const auto *
it : *trtcontainer) {
91 if (!colNext) {
msg(MSG::WARNING) <<
"newEvent(): !colNext " <<
endmsg;
continue; }
93 for (
const auto *circleit : *colNext){
97 event_data->m_listHits.push_back( circleit );
99 double onMyTime = circleit->timeOverThreshold();
100 if ( circleit->firstBinHigh() && (circleit->trailingEdge() != 24) && (circleit->trailingEdge() != 0) ) onMyTime = ( (
double) circleit->trailingEdge() + 1 ) * 3.125;
103 const Amg::Vector3D ¢er = circleit->detectorElement()->surface(circleit->identify()).center();
104 event_data->m_listHitCenter.push_back( center );
110 ATH_MSG_DEBUG(
"skipping high occupancy event of " << event_data->m_listHits.size() <<
" barrel hits, limit at "
115 ATH_MSG_DEBUG(
"newEvent(): Number of TRT barrel hits: " << event_data->m_listHits.size()
116 <<
" Number of hits with TOT > " <<
m_minSeedTOT <<
": " << event_data->m_listHitCenter.size() );
118 return std::unique_ptr<InDet::ITRT_TrackSegmentsMaker::IEventData>(event_data.release());
121 std::unique_ptr<InDet::ITRT_TrackSegmentsMaker::IEventData>
124 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::newRegion()" );
127 if (not trtcontainer.
isValid()) {
128 msg(MSG::ERROR) <<
"m_trtcontainer is empty!!!" <<
endmsg;
129 std::stringstream
msg;
131 throw std::runtime_error(
msg.str());
134 std::unique_ptr<TRT_TrackSegmentsMaker_BarrelCosmics::EventData>
135 event_data = std::make_unique<TRT_TrackSegmentsMaker_BarrelCosmics::EventData>(trtcontainer.
cptr());
139 for ( InDet::TRT_DriftCircleContainer::const_iterator
w = trtcontainer->indexFind(
d);
w!=trtcontainer->end(); ++
w ) {
140 for(
const auto *circleit : **
w) {
144 event_data->m_listHits.push_back(circleit);
146 double onMyTime = circleit->timeOverThreshold();
147 if ( circleit->firstBinHigh() && (circleit->trailingEdge() != 24) && (circleit->trailingEdge() != 0) ) onMyTime = ( (
double) circleit->trailingEdge() + 1 ) * 3.125;
149 const Amg::Vector3D ¢er = circleit->detectorElement()->surface(circleit->identify()).center();
150 event_data->m_listHitCenter.push_back( center );
156 ATH_MSG_DEBUG(
"skipping high occupancy event of " << event_data->m_listHits.size() <<
" barrel hits, limit at "
161 ATH_MSG_DEBUG(
"newRegion(): Number of TRT barrel hits: " << event_data->m_listHits.size()
162 <<
" Number of hits with TOT > " <<
m_minSeedTOT <<
": " << event_data->m_listHitCenter.size() );
164 return std::unique_ptr<InDet::ITRT_TrackSegmentsMaker::IEventData>(event_data.release());
171 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::endEvent()" );
175 msg(MSG::WARNING) <<
"endEvent() you called the function t create the segments but not retrived them later??" <<
endmsg;
176 msg(MSG::WARNING) <<
"endEvent() deleting remaining elements of m_segments" <<
endmsg;
194 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::find()" );
200 msg(MSG::WARNING) <<
"TRT_TrackSegmentsMaker_BarrelCosmics::find() probably called twice per event? or newEvent / newRegion have not been called. check your program" <<
endmsg;
201 event_data.
clear();
return;
204 std::vector<double> x0, phi, pivotX, pivotY, Xparabola, cotanParabola, InverseR;
205 std::vector<int> nHitsPosY, nHitsNegY;
208 int nIterations(15), countCalls(0);
209 while (countCalls<150) {
211 double xRange(1000.),
phiRange(M_PI_4);
212 double par[] = {0., M_PI_2, 0., 0., 0., 0., 0., 0.};
215 for (
int i=0;
i<nIterations;
i++) {
219 if ( !foundSeed )
break;
223 if ( xRange < 0.01 ||
phiRange < 0.00001)
break;
225 if (!foundSeed)
break;
230 int countAssociatedHits[] = {0, 0};
232 double sinphi = std::sqrt( 1. - cosphi*cosphi );
236 double measx[200], measy[200];
241 double a = (
par[3]-
it->x())*sinphi+(
it->y()-
par[4])*cosphi;
245 if (
m_magneticField && countMeas<200) { measx[countMeas] =
it->x(); measy[countMeas] =
it->y(); countMeas++; }
247 countAssociatedHits[(
it->y()>0)?0:1]++;
251 if ( countAssociatedHits[0]+countAssociatedHits[1] <
m_minHitsAboveTOT )
continue;
255 ATH_MSG_DEBUG(
"countAssociatedHits " << countAssociatedHits[0] <<
" "
257 x0.push_back(
par[0] ); phi.push_back(
par[1] ); nHitsPosY.push_back( countAssociatedHits[0] ); nHitsNegY.push_back( countAssociatedHits[1] );
259 pivotX.push_back(
par[3] ); pivotY.push_back(
par[4] ); Xparabola.push_back(
par[5] ); cotanParabola.push_back(
par[6] ); InverseR.push_back(
par[7] );
265 int nFoundSegments = x0.size();
if (nFoundSegments>10) nFoundSegments = 10;
267 for (
int i=0;
i<nFoundSegments;
i++) {
275 for (
unsigned int i=0;
i<event_data.
m_listHits.size();
i++) {
278 for (
int j=0; j<nFoundSegments; j++) {
280 if (nHitsPosY[j]<5 && center.y()>0.)
continue;
281 if (nHitsNegY[j]<5 && center.y()<0.)
continue;
284 double sinphi = std::sqrt(1./(1+cotanParabola[j]*cotanParabola[j]));
285 double cosphi = std::sqrt(1.-sinphi*sinphi);
if (cotanParabola[j]<0.) cosphi *= -1.;
286 double a = (pivotX[j]+Xparabola[j]-center.x())*sinphi+(center.y()-pivotY[j])*cosphi;
292 double sinphi = std::sqrt(1.-cosphi*cosphi);
293 residual = (x0[j]-center.x())*sinphi+center.y()*cosphi;
314 double mergeX0(100.), mergePhi(0.1);
315 for (
int i=0;
i<nFoundSegments;
i++) {
316 for (
int j=
i+1; j<nFoundSegments; j++) {
317 if ( std::abs(x0[
i]-x0[j])<mergeX0 && std::abs(phi[
i]-phi[j])<mergePhi ) {
320 mergeX0 = std::abs(x0[
i]-x0[j]);
321 mergePhi = std::abs(phi[
i]-phi[j]);
325 if (mergeI != mergeJ) {
326 ATH_MSG_DEBUG(
"Merge segments " << mergeI <<
" and " << mergeJ <<
" of size "
328 <<
"; difference in the impact par x: " << mergeX0 <<
" phi: " << mergePhi );
339 msg(
MSG::DEBUG) <<
"find() debug (" << nFoundSegments <<
")" ;
348 double trackpar[] = {x0[
i], phi[
i]};
366 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::next(): return "
384 double *bestParameters,
390 double searchWindow = (xbin>2.) ? xbin : 2.;
394 int binInX[100];
for (
int &
i : binInX)
i = 0;
398 double phi = phimin+(0.5+j)*phibin;
404 double transformX =
k.x() * sinphi -
k.y() * cosphi;
405 indexmin = (
int) ((transformX-transformXMin-searchWindow)/xbin);
406 indexmax = (
int) ((transformX-transformXMin+searchWindow)/xbin);
415 bestParameters[0] = ( xbin *
index + transformXMin) / sinphi;
416 bestParameters[1] = phi;
427 double sinphi = std::sqrt( 1. - cosphi*cosphi );
429 double parTransformX =
par[0] * sinphi;
431 double meanTransformY(0.);
432 int countMeanTransformY(0);
435 double transformX =
k.x() * sinphi -
k.y() * cosphi;
436 if ( std::abs(transformX-parTransformX) > 2. )
continue;
437 meanTransformY +=
k.x() * cosphi +
k.y() * sinphi;
438 countMeanTransformY++;
440 if (!countMeanTransformY) {
441 ATH_MSG_WARNING(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::findSeedInverseR(), no hits in the seed region???" );
444 meanTransformY /= (
double) countMeanTransformY;
453 double mean[] = { meanTransformY * cosphi + parTransformX * sinphi, meanTransformY * sinphi - parTransformX * cosphi };
454 int scanInverseR[101];
for (
int &
i : scanInverseR)
i = 0;
460 double transformX =
it.x() * sinphi -
it.y() * cosphi;
461 if ( std::abs(transformX-parTransformX) > 200. )
continue;
470 if (std::abs(
b)>0.0000001) {
471 double i1_tmp = ( window -
a ) /
b + 0.5;
472 double i2_tmp = ( -window -
a ) /
b + 0.5;
473 if (std::abs(i1_tmp)<1000.) { i1 = (
int) (std::ceil( i1_tmp )); i1 += 50; }
474 if (std::abs(i2_tmp)<1000.) { i2 = (
int) (std::ceil( i2_tmp )); i2 += 50; }
476 if (i1>100) { i1 = 100; }
else {
if (i1<0) i1 = 0; }
477 if (i2>100) { i2 = 100; }
else {
if (i2<0) i2 = 0; }
478 if (i1+i2==0 || i1+i2==200)
continue;
479 if (i1<=i2) {
for (
int i=i1;
i<=i2;
i++) scanInverseR[
i]++; }
480 else {
for (
int i=i2;
i<=i1;
i++) scanInverseR[
i]++; }
483 int iMax(-1), hitsMax(0);
484 for (
int i=0;
i<101;
i++)
if (scanInverseR[
i]>hitsMax) { iMax =
i; hitsMax = scanInverseR[
i]; }
486 par[2] = 0.00004 * (iMax-50);
521 double inverseSin3phi = 1. +
a[1]*
a[1]; inverseSin3phi *= std::sqrt(inverseSin3phi);
522 a[2] *= 2. / inverseSin3phi; }
536 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::convert() segment " << event_data.
m_segments.size()
537 <<
", N hits = " <<
hits.size());
539 if (
hits.size()<5) {
msg(MSG::ERROR) <<
"convert(): empty list of hits! size: " <<
hits.size() <<
endmsg;
return; }
545 int countOppositeSide(0);
553 if (countOppositeSide>5) {
554 ATH_MSG_DEBUG(
"convert(): removed " << countOppositeSide <<
" hits from the other side, N remaining hits: " <<
hits.size() );
557 ATH_MSG_WARNING(
"convert(): not enough hits after opposite side removal: " <<
hits.size() <<
", removed: "
558 << countOppositeSide );
563 double mean[10];
for (
double &
i :
mean)
i = 0.;
564 for (
auto & hit :
hits) {
566 mean[0] += (hit->detectorElement())->surface(hit->identify()).center().x();
567 mean[1] += (hit->detectorElement())->surface(hit->identify()).center().y();
569 for (
int i=0;
i<2;
i++)
mean[
i] /= (
double)
hits.size();
570 int iPivot(-1);
double yPivot(10000000.);
571 for (
unsigned int i=0;
i<
hits.size();
i++) {
584 if (
x2+
y2<yPivot) { yPivot =
x2+
y2; iPivot =
i; }
588 msg(MSG::ERROR) <<
"SF pivot index not found!!! " << yPivot <<
" " << iPivot <<
endmsg;
592 double cotanPhi =
mean[2] /
mean[4];
593 double phi =
std::atan(1./cotanPhi);
if (phi<0.) phi +=
M_PI;
595 ATH_MSG_DEBUG(
"compare parameters phi: " << trackpar[1] <<
" vs. " << phi );
617 double Xparabola =
a[0];
618 double cotanParabola =
a[1];
619 double inverseSin3phi = 1. +
a[1]*
a[1]; inverseSin3phi *= std::sqrt(inverseSin3phi);
620 double inverseR = 2. *
a[2] / inverseSin3phi;
623 msg(
MSG::DEBUG) <<
"TRT_TrackSegmentsMaker_BarrelCosmics: parabola fit, X: " << Xparabola <<
endmsg;
624 msg(
MSG::DEBUG) <<
" parabola fit, cotan: " << cotanParabola <<
" compare to " << cotanPhi <<
endmsg;
628 qOverp = inverseR / 0.6;
638 double f33 = 4. / ( 3. * (1.+cotanPhi*cotanPhi) *
mean[4] );
641 0. ,45633., 0., 0., 0.,
642 0. , 0., f33, 0., 0.,
643 0. , 0., 0., 0.2, 0.,
647 (
hits[iPivot]->detectorElement())->surface(
hits[iPivot]->
identify()).center().
z() );
656 if (phi>0.) phi -=
M_PI;
657 if (phi<-M_PI || phi>0.)
msg(MSG::ERROR) <<
"phi value problem: " << phi <<
endmsg;
669 for (
const auto *DC :
hits) {
706 Amg::Vector3D faketransl(firstcenter.x(),firstcenter.y()-5.,firstcenter.z());
711 std::move(pseudoPar),
712 std::move(pseudocov),
714 rio.push_back( pseudo );
715 delete pseudoSurface;
719 chi2 /= ( 1. + cotanPhi*cotanPhi );
740 if (nhits<10)
return;
742 double shift[] = {0., 0.};
743 for (
int i=0;
i<nhits;
i++) { shift[0] += measx[
i]; shift[1] += measy[
i]; }
744 for (
double &
i : shift)
i /= (
double) nhits;
745 for (
int i=0;
i<nhits;
i++) { measx[
i] -= shift[0]; measy[
i] -= shift[1]; }
747 double mean[10];
for (
double &
i :
mean)
i = 0.;
748 for (
int i=0;
i<nhits;
i++) {
749 double x2 = measx[
i]*measx[
i];
750 double y2 = measy[
i]*measy[
i];
753 mean[2] += measx[
i]*measy[
i];
779 double Xparabola =
a[0];
780 double cotanParabola =
a[1];
781 double inverseSin3phi = 1. +
a[1]*
a[1]; inverseSin3phi *= std::sqrt(inverseSin3phi);
782 double inverseR = 2. *
a[2] / inverseSin3phi;
783 double sinphi = std::sqrt(1./(1+
a[1]*
a[1]));
784 double cosphi = std::sqrt(1.-sinphi*sinphi);
if (cotanParabola<0.) cosphi *= -1.;
789 result[3] = cotanParabola;
794 for (
int i=0;
i<nhits;
i++) {
795 double tmp = (Xparabola-measx[
i])*sinphi+measy[
i]*cosphi;
801 for (
int i=0;
i<nhits;
i++) { measx[
i] += shift[0]; measy[
i] += shift[1]; }
815 ATH_MSG_DEBUG(
"InDet::TRT_TrackSegmentsMaker_BarrelCosmics::find()");
820 ATH_MSG_WARNING(
"find probably called twice per event? or newEvent / newRegion have not been called. check your program" );
821 event_data.
clear();
return;
824 std::vector<double> x0, phi;
825 std::vector<int> nHitsPosY, nHitsNegY;
828 int nIterations(15), countCalls(0);
829 while (countCalls<150) {
831 double xRange(1000.),
phiRange(M_PI_4);
832 double par[] = {0., M_PI_2};
835 for (
int i=0;
i<nIterations;
i++) {
839 if ( !foundSeed )
break;
843 if ( xRange < 0.01 ||
phiRange < 0.00001)
break;
846 if (!foundSeed)
break;
849 int countAssociatedHits[] = {0, 0};
851 double sinphi = std::sqrt(1.-cosphi*cosphi);
855 if ( std::abs( (
par[0]-
it->x())*sinphi +
it->y()*cosphi ) > 2. ) { ++
it;
continue; }
856 countAssociatedHits[(
it->y()>0)?0:1]++;
860 if ( countAssociatedHits[0]+countAssociatedHits[1] <
m_minHitsAboveTOT )
continue;
862 x0.push_back(
par[0] ); phi.push_back(
par[1] ); nHitsPosY.push_back( countAssociatedHits[0] ); nHitsNegY.push_back( countAssociatedHits[1] );
868 int nFoundSegments = x0.size();
869 if (nFoundSegments>10) nFoundSegments = 10;
870 for (
int i=0;
i<nFoundSegments;
i++) {
874 for (
unsigned int i=0;
i<event_data.
m_listHits.size();
i++) {
876 center = event_data.
m_listHits[
i]->detectorElement()->surface(event_data.
m_listHits[
i]->identify()).center();
878 for (
int j=0; j<nFoundSegments; j++) {
879 if (nHitsPosY[j]<5 && center.y()>0.)
continue;
880 if (nHitsNegY[j]<5 && center.y()<0.)
continue;
882 double sinphi = std::sqrt(1.-cosphi*cosphi);
883 if ( std::abs((x0[j]-center.x())*sinphi+center.y()*cosphi) < 2.) {
893 msg(
MSG::DEBUG) <<
"find() debug (" << nFoundSegments <<
")" ;
903 double trackpar[] = {x0[
i], phi[
i]};