36 const std::string& name,
37 const IInterface* parent)
42 declareInterface<IDerivCalcTool>(
this);
57 msg(MSG::DEBUG) <<
"in ShiftingDerivCalcTool initialize()"<<
endmsg;
78 return StatusCode::SUCCESS;
96 return StatusCode::SUCCESS;
101 const std::vector<AlignModule*>& alignModules)
121 const Track* refittedTrack =
m_fitter->alignmentFit(alignCache, *trackForRefit,
124 if (!refittedTrack) {
125 msg(MSG::WARNING) <<
"initial track refit failed" <<
endmsg;
139 for (std::vector<AlignModule*>::const_iterator moduleIt=alignModules.begin();
140 moduleIt!=alignModules.end(); ++moduleIt) {
145 alignParIt!=alignPars->
end(); ++alignParIt) {
147 for (
int ishift=0;ishift<2;ishift++) {
149 double shiftsize =
shiftSize(*alignParIt);
150 if (ishift>0) shiftsize*=-1.;
151 m_alignModuleTool->shiftModule(*moduleIt,alignTrack,(**alignParIt).paramType(),shiftsize);
152 refittedTrack = (
m_fitter->fit(Gaudi::Hive::currentContext(),
156 if (!refittedTrack) {
157 msg(MSG::WARNING) <<
"track refit failed!"<<
endmsg;
197 if (!trackForRefit) {
202 const Track* refittedTrack =
m_fitter->alignmentFit( alignCache,
207 if (!refittedTrack) {
216 msg()<<MSG::DEBUG<<
"local Chi2(unshifted) in setChi2VAlignParam="<<localChi2<<
endmsg;
237 for (; atsosItr != alignTrack->
lastAtsos(); ++atsosItr) {
238 if (!(**atsosItr).isValid())
continue;
239 for (std::vector<Residual>::const_iterator itRes=(**atsosItr).firstResidual();
240 itRes!=(**atsosItr).lastResidual();++itRes,++imeas) {
241 double residual = itRes->residual();
242 double errSq = itRes->errSq();
243 (*m_unshiftedResiduals)[imeas]=residual;
244 (*m_unshiftedResErrors)[imeas]=std::sqrt(errSq);
251 msg(MSG::ERROR)<<
"problem with nmeas, imeas="<<imeas<<
", NMEAS="<<NMEAS<<
endmsg;
252 throw std::runtime_error(
"Error in ShiftingDerivCalcTool::setUnshiftedResiduals");
256 delete refittedTrack; refittedTrack=
nullptr;
269 std::vector<AlignModule*> alignModules;
271 atsosItr != alignTrack->
lastAtsos(); ++atsosItr) {
280 if (!(*atsosItr)->isValid() || !module)
continue;
281 if (
find(alignModules.begin(),alignModules.end(),module) == alignModules.end())
282 alignModules.push_back(module);
302 std::vector<AlignModuleDerivatives> * derivatives =
new std::vector<AlignModuleDerivatives>;
303 std::vector<AlignModuleDerivatives> * derivativeErr =
new std::vector<AlignModuleDerivatives>;
304 std::vector<std::pair<AlignModule*, std::vector<double> > > * actualSecondDerivatives =
305 new std::vector<std::pair<AlignModule*, std::vector<double> > >;
307 for (
auto *alignModule : alignModules) {
309 ATH_MSG_DEBUG(
"finding derivatives for module "<<(*alignModule).identify());
311 std::vector<Amg::VectorX> deriv_vec;
312 std::vector<Amg::VectorX> derivErr_vec;
313 std::vector<double> actualsecderiv_vec;
317 const int nAlignPar = alignPars->
size();
328 bool resetIPar=
false;
329 std::vector<Amg::VectorX> tmpderiv_vec;
330 std::vector<Amg::VectorX> tmpderivErr_vec;
331 std::vector<double> tmpactualsecderiv_vec;
336 alignTrack, alignModule,
337 tmpderiv_vec,tmpderivErr_vec,tmpactualsecderiv_vec,
341 delete derivativeErr;
342 delete actualSecondDerivatives;
352 tmpderiv_vec,tmpderivErr_vec,tmpactualsecderiv_vec,
358 delete derivativeErr;
359 delete actualSecondDerivatives;
369 tmpderiv_vec,tmpderivErr_vec,tmpactualsecderiv_vec,
375 delete derivativeErr;
376 delete actualSecondDerivatives;
383 if (success && !resetIPar) {
384 for (
int i=0;i<(int)tmpderiv_vec.size();i++) {
385 deriv_vec.push_back(tmpderiv_vec[i]);
386 derivErr_vec.push_back(tmpderivErr_vec[i]);
387 actualsecderiv_vec.push_back(tmpactualsecderiv_vec[i]);
392 delete derivativeErr;
393 delete actualSecondDerivatives;
412 derivatives->push_back(make_pair(alignModule,deriv_vec));
413 derivativeErr->push_back(make_pair(alignModule,derivErr_vec));
414 actualSecondDerivatives->push_back(make_pair(alignModule,actualsecderiv_vec));
435 double& actualSecondDeriv)
445 ATH_MSG_ERROR(
"set m_fitter before calling getDerivatives (by calling setUnshiftedResiduals)");
452 module->setNChamberShifts(m_nFits);
455 double** residuals=
new double*[NFITS];
456 double** resErrors=
new double*[NFITS];
457 double* chi2Array =
new double[NFITS];
458 double* chi2ArrayX=
new double[NFITS];
465 for (
int ifit=0;ifit<NFITS;ifit++) {
466 residuals[ifit]=
new double[NMEAS];
467 resErrors[ifit]=
new double[NMEAS];
473 ATH_MSG_DEBUG(
"chi2Array["<<unshiftedTrackIndex<<
"]="<<chi2Array[unshiftedTrackIndex]);
474 chi2ArrayX[unshiftedTrackIndex] = 0.;
491 for (
int ifit=0;ifit<NFITS;ifit++) {
495 if (ifit>unshiftedTrackIndex) {
496 jfit=NFITS-ifit+unshiftedTrackIndex;
498 if (
m_doFits && ifit==unshiftedTrackIndex) {
500 residuals[ifit][i]=(*m_unshiftedResiduals)[i];
501 resErrors[ifit][i]=(*m_unshiftedResErrors)[i];
509 double currentshift = 0.;
511 currentshift = shiftsize * (double)(jfit-unshiftedTrackIndex);
513 currentshift = (ifit==0) ? -1.*shiftsize : shiftsize;
515 ATH_MSG_DEBUG(
"current shift="<<currentshift<<
" in getDerivatives");
522 const Track* refittedTrack=
m_fitter->alignmentFit(alignCache,
532 delete [] residuals;
delete [] resErrors;
533 delete [] chi2Array;
delete [] chi2ArrayX;
550 if (!refittedTrack) {
551 msg(MSG::WARNING) <<
"track refit failed for jfit "<<jfit <<
endmsg;
552 delete [] residuals;
delete [] resErrors;
553 delete [] chi2Array;
delete [] chi2ArrayX;
571 chi2ArrayX[jfit]= shiftsize * (double)(jfit-unshiftedTrackIndex);
572 chi2Array[jfit]=localChi2;
586 for (; atsosItr != alignTrack->
lastAtsos(); ++atsosItr) {
587 if (!(*atsosItr)->isValid())
continue;
588 for (std::vector<Residual>::const_iterator itRes=(**atsosItr).firstResidual();
589 itRes!=(**atsosItr).lastResidual();++itRes,++imeas) {
592 residuals[jfit][imeas]=itRes->residual();
593 resErrors[jfit][imeas]=std::sqrt(itRes->errSq());
596 residuals[jfit][imeas]=resErrors[jfit][imeas]=0.;
598 ATH_MSG_DEBUG(
"residuals["<<jfit<<
"]["<<imeas<<
"]="<<residuals[jfit][imeas]);
599 ATH_MSG_DEBUG(
"resErrors["<<jfit<<
"]["<<imeas<<
"]="<<resErrors[jfit][imeas]);
603 delete refittedTrack; refittedTrack=
nullptr;
610 for (; aatsosItr != alignTrack->
lastAtsos(); ++aatsosItr) {
611 if (!(*aatsosItr)->isValid())
continue;
612 for (std::vector<Residual>::const_iterator itRes=(**aatsosItr).firstResidual();
613 itRes!=(**aatsosItr).lastResidual();++itRes,++iimeas) {
614 for (
int ifit=0;ifit<NFITS;ifit++) {
615 ATH_MSG_DEBUG(
"["<<ifit<<
"]["<<iimeas<<
"] res="<<residuals[ifit][iimeas]<<
616 ", resErr="<<resErrors[ifit][iimeas]);
623 delete [] residuals;
delete [] resErrors;
624 delete [] chi2Array;
delete [] chi2ArrayX;
632 TGraph*
gr =
new TGraph(
m_nFits,chi2ArrayX,chi2Array);
633 gr->Fit(
"pol2",
"QF");
634 TF1* fit=
gr->GetFunction(
"pol2");
635 double chi2 =fit->GetChisquare()/double(
m_nFits-3);
636 double slope=fit->GetParameter(1);
637 actualSecondDeriv=fit->GetParameter(2);
644 if (
chi2>1.e-6 || std::fabs(slope)<1.e-10) {
646 StatusCode
sc=
evtStore()->retrieve(eventInfo);
662 ATH_MSG_DEBUG(
"created derivatives with "<<derivatives.rows()<<
" rows");
667 delete [] residuals;
delete [] resErrors;
668 delete [] chi2Array;
delete [] chi2ArrayX;
682 return emptyDerivatives;
686 TCanvas* canv(
nullptr);
687 std::vector<TGraph*> vecGraphs;
689 for (; atsosItr != alignTrack->
lastAtsos(); ++atsosItr) {
690 if (!(*atsosItr)->isValid())
continue;
691 for (
int idim=0;idim<(*atsosItr)->nResDim();idim++) {
693 double* gr_x =
new double[NFITS];
694 double* gr_y =
new double[NFITS];
696 for (
int ifit=0;ifit<NFITS;ifit++) {
697 double residual=residuals[ifit][imeas];
698 double resError=resErrors[ifit][imeas];
699 if (residual>-999.) {
700 gr_x[ngoodfits] =chi2ArrayX[ifit];
701 gr_y[ngoodfits] =residual/resError;
707 derivatives[imeas]=(residuals[1][imeas]-residuals[0][imeas])/(2.*shiftsize)*
708 resErrors[unshiftedTrackIndex][imeas];
711 TGraph*
gr=
new TGraph(ngoodfits,gr_x,gr_y);
714 gr->Fit(
"pol2",
"VF");
716 gr->Fit(
"pol2",
"QF");
717 TF1* fit=
gr->GetFunction(
"pol2");
720 ATH_MSG_DEBUG(
"deriv["<<imeas<<
"]="<<fit->GetParameter(1)<<
" +/- "<<fit->GetParError(1)
721 <<
", chi2="<<fit->GetChisquare());
722 derivatives[imeas]=fit->GetParameter(1)*resErrors[unshiftedTrackIndex][imeas];
723 derivativeErr[imeas]=fit->GetParError(1)*resErrors[unshiftedTrackIndex][imeas];
728 if (!canv) canv=
new TCanvas(
"resPlots",
"resPlots");
730 gr->SetMarkerStyle(20);
733 gr->GetXaxis()->SetTitle(
"shift in chamber pos. from nominal (CLHEP::mm)");
734 gr->GetYaxis()->SetTitle(
"residual (CLHEP::mm)");
736 TPaveText* pave=
new TPaveText(.4,.65,.97,.92,
"NDC");
737 pave->SetFillColor(0);
738 pave->SetBorderSize(1);
739 std::stringstream measType; measType<<
"meas type: ";
743 else measType<<
" undefined";
745 pave->AddText(measType.str().c_str());
747 std::stringstream firstderivtxt,secndderivtxt,aptxt,chi2txt;
748 firstderivtxt<<fit->GetParameter(1)<<
" +/- "<<fit->GetParError(1);
749 secndderivtxt<<fit->GetParameter(2)<<
" +/- "<<fit->GetParError(2);
750 aptxt <<
"alignPar "<<alignPar->
paramType()<<
", RIO in "<<(*atsosItr)->identify();
751 chi2txt<<
"chi2="<<fit->GetChisquare();
753 pave->AddText(firstderivtxt.str().c_str());
754 pave->AddText(secndderivtxt.str().c_str());
755 pave->AddText(aptxt.str().c_str());
756 pave->AddText(chi2txt.str().c_str());
759 std::stringstream canvName;
760 canvName<<
"resPlots_ap"<<alignPar->
paramType()<<
"_measType"
761 <<(*atsosItr)->measType()<<
"_"<<imeas<<
".eps";
762 canv->Print(canvName.str().c_str());
767 vecGraphs.push_back(
gr);
770 derivatives[imeas]=-999.;
771 derivativeErr[imeas]=-999.;
782 for (
auto & vecGraph : vecGraphs)
790 for (
int ifit=0;ifit<NFITS;ifit++) {
809 double sigma=alignPar->
sigma();
810 return shift * sigma;
819 ATH_MSG_ERROR(
"Need to assign this matrix correctly: ShiftingDerivCalcTool.cxx:888");
828 const double epsilon=1e-10;
829 for(
int irow=0; irow<W.rows(); ++irow) {
830 Wisvalid = Wisvalid && W(irow,irow)>0;
831 if( !(W(irow,irow)>0) )
832 msg(MSG::WARNING) <<
"matrix invalid: " << W(irow,irow) <<
endmsg;
834 for(
int icol=0; icol<=irow; ++icol) {
837 double Wcorr = W(irow,icol)/sqrt(W(irow,irow)*W(icol,icol));
838 bool Wcorrisvalid = Wcorr+epsilon>=-1 && Wcorr-epsilon<=1;
839 Wisvalid = Wisvalid && Wcorrisvalid;
841 msg(MSG::WARNING) <<
"matrix corr invalid: " << Wcorr-1 <<
" " << Wcorr+1 <<
endmsg;
864 delete [] i; i=
nullptr;
873 std::vector<Amg::VectorX>& deriv_vec,
874 std::vector<Amg::VectorX>& derivErr_vec,
875 std::vector<double>& actualsecderiv_vec,
881 derivErr_vec.clear();
882 actualsecderiv_vec.clear();
891 double actualSecondDeriv(0.);
896 if (resetIPar)
continue;
898 if (
vec.rows()<1)
return false;
900 deriv_vec.push_back(
vec);
901 derivErr_vec.push_back(derivErr);
902 actualsecderiv_vec.push_back(actualSecondDeriv);
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
std::vector< size_t > vec
ServiceHandle< StoreGateSvc > & evtStore()
DataModel_detail::const_iterator< DataVector > const_iterator
DataModel_detail::iterator< DataVector > iterator
Standard 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.
double sigma() const
returns sigma
AlignModule::TransformParameters paramType() const
returns the type of parameter (i.e.
const AlignModule * alignModule() const
returns the AlignModule
void setWeightMatrix(Amg::SymMatrixX *mat)
AlignTSOSCollection::const_iterator lastAtsos() const
returns iterator pointer to last element in collection
const Amg::SymMatrixX * localErrorMatrixInv() const
inverse local error matrix, calculated by AlignTrack by calling atsos->hitDistanceVar()
int nAlignTSOSMeas() const
number of alignTSOS (including scatterers if included on AlignTrack
void setActualSecondDerivatives(std::vector< std::pair< AlignModule *, std::vector< double > > > *vec)
void setTrackAlignParamQuality(int i, double val)
void setDerivatives(std::vector< AlignModuleDerivatives > *vec)
AlignTSOSCollection::const_iterator firstAtsos() const
retrieve iterator pointer to first element in collection
void setWeightMatrixFirstDeriv(Amg::SymMatrixX *mat)
const Trk::Track * trackWithoutScattering() const
returns track with ScatteringAngle pointers all set to zero (used for refit by iPat)
void setDerivativeErr(std::vector< AlignModuleDerivatives > *vec)
void setResidualVector(Amg::VectorX *vec)
bool isSLTrack() const
method to determine whether a straight line track or not
double chiSquared() const
returns the of the overall track fit
const FitQuality * fitQuality() const
return a pointer to the fit quality const-overload
uint32_t runNumber() const
The current event's run number.
uint64_t eventNumber() const
The current event's event number.
double chi2(TH1 *h0, TH1 *h1)
std::string find(const std::string &s)
return a remapped string
Eigen::Matrix< double, Eigen::Dynamic, Eigen::Dynamic > MatrixX
Dynamic Matrix - dynamic allocation.
Eigen::Matrix< double, Eigen::Dynamic, 1 > VectorX
Dynamic Vector - dynamic allocation.
constexpr ParticleHypothesis particle[PARTICLEHYPOTHESES]
the array of masses
@ NumberOfMeasurementTypes
Ensure that the ATLAS eigen extensions are properly loaded.
EventInfo_v1 EventInfo
Definition of the latest event info version.
int m_minIterations
sets the minimum number of iterations to be used in the track fit.
int m_iterationsOfLastFit
returns the number of iterations used by the last fit (count starts at 1 for a single-iteration fit)
int run(int argc, char *argv[])