CMS 3D CMS Logo

MuonMillepedeAlgorithm.cc
Go to the documentation of this file.
1 #include <fstream>
2 
3 #include "TFile.h"
4 #include "TTree.h"
5 #include "TKey.h"
6 
11 
14 
27 
29 
31 
32 // Constructor ----------------------------------------------------------------
33 
35  // parse parameters
36 
37  edm::LogWarning("Alignment") << "[MuonMillepedeAlgorithm] constructed.";
38 
39  collec_f = cfg.getParameter<std::string>("CollectionFile");
40 
41  isCollectionJob = cfg.getParameter<bool>("isCollectionJob");
42 
43  collec_path = cfg.getParameter<std::string>("collectionPath");
44 
45  collec_number = cfg.getParameter<int>("collectionNumber");
46 
47  outputCollName = cfg.getParameter<std::string>("outputCollName");
48 
49  ptCut = cfg.getParameter<double>("ptCut");
50 
51  chi2nCut = cfg.getParameter<double>("chi2nCut");
52 }
53 
54 // Call at beginning of job ---------------------------------------------------
55 
59  AlignableExtras *extras,
60  AlignmentParameterStore *store) {
61  edm::LogWarning("Alignment") << "[MuonMillepedeAlgorithm] Initializing...";
62 
63  // accessor Det->AlignableDet
64  theAlignableDetAccessor = new AlignableNavigator(tracker, muon);
65 
66  // set alignmentParameterStore
68 
69  // get alignables
71 }
72 
74  std::map<std::string, TMatrixD *> map;
75 
76  for (int c_job = 0; c_job < collec_number; ++c_job) {
77  char name_f[40];
78  snprintf(name_f, sizeof(name_f), "%s_%d/%s", collec_path.c_str(), c_job, collec_f.c_str());
79  TFile file_it(name_f);
80 
81  if (file_it.IsZombie())
82  continue;
83 
84  TList *m_list = file_it.GetListOfKeys();
85  if (m_list == nullptr) {
86  return;
87  }
88  TKey *index = (TKey *)m_list->First();
89  if (index == nullptr) {
90  }
91  if (index != nullptr) {
92  do {
93  std::string objectName(index->GetName());
94  TMatrixD *mat = (TMatrixD *)index->ReadObj();
95  std::map<std::string, TMatrixD *>::iterator node = map.find(objectName);
96  if (node == map.end()) {
97  TMatrixD *n_mat = new TMatrixD(mat->GetNrows(), mat->GetNcols());
98  map.insert(make_pair(objectName, n_mat));
99  }
100  *(map[objectName]) += *mat;
101  index = (TKey *)m_list->After(index);
102  } while (index != nullptr);
103  }
104  file_it.Close();
105  }
106 
107  TFile theFile2(outputCollName.c_str(), "recreate");
108  theFile2.cd();
109 
110  std::map<std::string, TMatrixD *>::iterator m_it = map.begin();
111  for (; m_it != map.end(); ++m_it) {
112  if (m_it->first.find("_invCov") != std::string::npos) {
113  std::string id_s = m_it->first.substr(0, m_it->first.find("_invCov"));
114  std::string id_w = id_s + "_weightRes";
115  std::string id_n = id_s + "_N";
116  std::string cov = id_s + "_cov";
117  std::string sol = id_s + "_sol";
118 
119  //Covariance calculation
120  TMatrixD invMat(m_it->second->GetNrows(), m_it->second->GetNcols());
121  invMat = *(m_it->second);
122  invMat.Invert();
123  //weighted residuals
124  TMatrixD weightMat(m_it->second->GetNcols(), 1);
125  weightMat = *(map[id_w]);
126  //Solution of the linear system
127  TMatrixD solution(m_it->second->GetNrows(), 1);
128  solution = invMat * weightMat;
129  //Number of Tracks
130  TMatrixD n(1, 1);
131  n = *(map[id_n]);
132 
133  invMat.Write(cov.c_str());
134  n.Write(id_n.c_str());
135  solution.Write(sol.c_str());
136  }
137  }
138  theFile2.Write();
139  theFile2.Close();
140 }
141 
142 // Call at end of job ---------------------------------------------------------
143 
145  if (isCollectionJob) {
146  this->collect();
147  return;
148  }
149 
150  edm::LogWarning("Alignment") << "[MuonMillepedeAlgorithm] Terminating";
151 
152  // iterate over alignment parameters
153  for (const auto &ali : theAlignables) {
154  // Alignment parameters
155  // AlignmentParameters* par = ali->alignmentParameters();
156  edm::LogInfo("Alignment") << "now apply params";
158  // set these parameters 'valid'
159  ali->alignmentParameters()->setValid(true);
160  }
161 
162  edm::LogWarning("Alignment") << "[MuonMillepedeAlgorithm] Writing aligned parameters to file: "
163  << theAlignables.size();
164 
165  TFile *theFile = new TFile(collec_f.c_str(), "recreate");
166  theFile->cd();
167  std::map<std::string, AlgebraicMatrix *>::iterator invCov_it = map_invCov.begin();
168  std::map<std::string, AlgebraicMatrix *>::iterator weightRes_it = map_weightRes.begin();
169  std::map<std::string, AlgebraicMatrix *>::iterator n_it = map_N.begin();
170  for (; n_it != map_N.end(); ++invCov_it, ++weightRes_it, ++n_it) {
171  TMatrixD tmat_invcov(0, 0);
172  this->toTMat(invCov_it->second, &tmat_invcov);
173  TMatrixD tmat_weightres(0, 0);
174  this->toTMat(weightRes_it->second, &tmat_weightres);
175  TMatrixD tmat_n(0, 0);
176  this->toTMat(n_it->second, &tmat_n);
177 
178  tmat_invcov.Write(invCov_it->first.c_str());
179  tmat_weightres.Write(weightRes_it->first.c_str());
180  tmat_n.Write(n_it->first.c_str());
181  }
182 
183  theFile->Write();
184  theFile->Close();
185 }
186 
187 void MuonMillepedeAlgorithm::toTMat(AlgebraicMatrix *am_mat, TMatrixD *tmat_mat) {
188  tmat_mat->ResizeTo(am_mat->num_row(), am_mat->num_col());
189  for (int c_i = 0; c_i < am_mat->num_row(); ++c_i) {
190  for (int c_j = 0; c_j < am_mat->num_col(); ++c_j) {
191  (*tmat_mat)(c_i, c_j) = (*am_mat)[c_i][c_j];
192  }
193  }
194 }
195 
196 // Run the algorithm on trajectories and tracks -------------------------------
197 
199  if (isCollectionJob) {
200  return;
201  }
202 
203  // loop over tracks
204  //int t_counter = 0;
206  for (ConstTrajTrackPairCollection::const_iterator it = tracks.begin(); it != tracks.end(); it++) {
207  const Trajectory *traj = (*it).first;
208  const reco::Track *track = (*it).second;
209 
210  float pt = track->pt();
211  float chi2n = track->normalizedChi2();
212 #ifdef EDM_ML_DEBUG
213  float eta = track->eta();
214  float phi = track->phi();
215  //int ndof = track->ndof();
216  int nhit = track->numberOfValidHits();
217 
218  LogDebug("Alignment") << "New track pt,eta,phi,chi2n,hits: " << pt << "," << eta << "," << phi << "," << chi2n
219  << "," << nhit;
220 #endif
221 
222  //Accept or not accept the track
223  if (pt > ptCut && chi2n < chi2nCut) {
224  std::vector<const TransientTrackingRecHit *> hitvec;
225  std::vector<TrajectoryStateOnSurface> tsosvec;
226 
227  std::vector<TrajectoryMeasurement> measurements = traj->measurements();
228 
229  //In this loop the measurements and hits are extracted and put on two vectors
230  for (std::vector<TrajectoryMeasurement>::iterator im = measurements.begin(); im != measurements.end(); im++) {
231  TrajectoryMeasurement meas = *im;
232  const TransientTrackingRecHit *hit = &(*meas.recHit());
233  //We are not very strict at this point
235  //***Forward
236  const TrajectoryStateOnSurface &tsos = meas.forwardPredictedState();
237  if (tsos.isValid()) {
238  hitvec.push_back(hit);
239  tsosvec.push_back(tsos);
240  }
241  }
242  }
243 
244  // transform RecHit vector to AlignableDet vector
245  std::vector<AlignableDetOrUnitPtr> alidetvec = theAlignableDetAccessor->alignablesFromHits(hitvec);
246 
247  // get concatenated alignment parameters for list of alignables
249 
250  std::vector<TrajectoryStateOnSurface>::const_iterator itsos = tsosvec.begin();
251  std::vector<const TransientTrackingRecHit *>::const_iterator ihit = hitvec.begin();
252 
253  //int ch_counter = 0;
254 
255  while (itsos != tsosvec.end()) {
256  // get AlignableDet for this hit
257  const GeomDet *det = (*ihit)->det();
259 
260  // get relevant Alignable
261  Alignable *ali = aap.alignableFromAlignableDet(alidet);
262 
263  //To be sure that the ali is not null and that it's a DT segment
264  if (ali != nullptr && (*ihit)->geographicalId().subdetId() == 1) {
265  DTChamberId m_Chamber(det->geographicalId());
266  //Station 4 does not contain Theta SL
267  if ((*ihit)->dimension() == 4 || ((*ihit)->dimension() == 2 && m_Chamber.station() == 4))
268  //if((*ihit)->dimension() == 4)
269  {
270  edm::LogInfo("Alignment") << "Entrando";
271 
273 
274  edm::LogInfo("Alignment") << "Entrando";
275  //(dx/dz,dy/dz,x,y) for a 4DSegment
276  AlgebraicVector ihit4D = (*ihit)->parameters();
277 
278  //The innerMostState always contains the Z
279  //(q/pt,dx/dz,dy/dz,x,y)
280  AlgebraicVector5 alivec = (*itsos).localParameters().mixedFormatVector();
281 
282  //The covariance matrix follows the sequence
283  //(q/pt,dx/dz,dy/dz,x,y) but we reorder to
284  //(x,y,dx/dz,dy/dz)
285  AlgebraicSymMatrix55 rawCovMat = (*itsos).localError().matrix();
286  AlgebraicMatrix CovMat(4, 4);
287  int m_index[] = {2, 3, 0, 1};
288  for (int c_ei = 0; c_ei < 4; ++c_ei) {
289  for (int c_ej = 0; c_ej < 4; ++c_ej) {
290  CovMat[m_index[c_ei]][m_index[c_ej]] = rawCovMat(c_ei + 1, c_ej + 1);
291  }
292  }
293 
294  int inv_check;
295  //printM(CovMat);
296  CovMat.invert(inv_check);
297  if (inv_check != 0) {
298  edm::LogError("Alignment") << "Covariance Matrix inversion failed";
299  return;
300  }
301 
302  //The order is changed to:
303  // (x,0,dx/dz,0) MB4 Chamber
304  // (x,y,dx/dz,dy/dz) Not MB4 Chamber
305  AlgebraicMatrix residuals(4, 1);
306  if (m_Chamber.station() == 4) {
307  //Filling Residuals
308  residuals[0][0] = ihit4D[2] - alivec[3];
309  residuals[1][0] = 0.0;
310  residuals[2][0] = ihit4D[0] - alivec[1];
311  residuals[3][0] = 0.0;
312  //The error in the Theta coord is set to infinite
313  CovMat[1][0] = 0.0;
314  CovMat[1][1] = 0.0;
315  CovMat[1][2] = 0.0;
316  CovMat[1][3] = 0.0;
317  CovMat[0][1] = 0.0;
318  CovMat[2][1] = 0.0;
319  CovMat[3][1] = 0.0;
320  CovMat[3][0] = 0.0;
321  CovMat[3][2] = 0.0;
322  CovMat[3][3] = 0.0;
323  CovMat[0][3] = 0.0;
324  CovMat[2][3] = 0.0;
325  } else {
326  //Filling Residuals
327  residuals[0][0] = ihit4D[2] - alivec[3];
328  residuals[1][0] = ihit4D[3] - alivec[4];
329  residuals[2][0] = ihit4D[0] - alivec[1];
330  residuals[3][0] = ihit4D[1] - alivec[2];
331  }
332 
333  // Derivatives
334  AlgebraicMatrix derivsAux = params->selectedDerivatives(*itsos, alidet);
335 
336  std::vector<bool> mb4_mask;
337  std::vector<bool> selection;
338  //To be checked
339  mb4_mask.push_back(true);
340  mb4_mask.push_back(false);
341  mb4_mask.push_back(true);
342  mb4_mask.push_back(true);
343  mb4_mask.push_back(true);
344  mb4_mask.push_back(false);
345  selection.push_back(true);
346  selection.push_back(true);
347  selection.push_back(false);
348  selection.push_back(false);
349  selection.push_back(false);
350  selection.push_back(false);
351  int nAlignParam = 0;
352  if (m_Chamber.station() == 4) {
353  for (int icor = 0; icor < 6; ++icor) {
354  if (mb4_mask[icor] && selection[icor])
355  nAlignParam++;
356  }
357  } else {
358  nAlignParam = derivsAux.num_row();
359  }
360 
361  AlgebraicMatrix derivs(nAlignParam, 4);
362  if (m_Chamber.station() == 4) {
363  int der_c = 0;
364  for (int icor = 0; icor < 6; ++icor) {
365  if (mb4_mask[icor] && selection[icor]) {
366  for (int ccor = 0; ccor < 4; ++ccor) {
367  derivs[der_c][ccor] = derivsAux[icor][ccor];
368  ++der_c;
369  }
370  }
371  }
372  } else {
373  derivs = derivsAux;
374  }
375 
376  //for(int co = 0; co < derivs.num_row(); ++co)
377  //{
378  // for(int ci = 0; ci < derivs.num_col(); ++ci)
379  // {
380  // edm::LogInfo("Alignment") << "Derivatives: " << co << " " << ci << " " << derivs[co][ci] << " ";
381  // }
382  //}
383 
384  AlgebraicMatrix derivsT = derivs.T();
385  AlgebraicMatrix invCov = derivs * CovMat * derivsT;
386  AlgebraicMatrix weightRes = derivs * CovMat * residuals;
387 
388  //this->printM(derivs);
389  //this->printM(CovMat);
390  //this->printM(residuals);
391 
392  char name[40];
393  snprintf(
394  name, sizeof(name), "Chamber_%d_%d_%d", m_Chamber.wheel(), m_Chamber.station(), m_Chamber.sector());
395  std::string chamId(name);
396  //MB4 need a special treatment
397  /*AlgebraicMatrix invCovMB4(2,2);
398  AlgebraicMatrix weightResMB4(2,1);
399  if( m_Chamber.station() == 4 )
400  {
401  int m_index_2[] = {0,2};
402  for(int c_i = 0; c_i < 2; ++c_i)
403  {
404  weightResMB4[c_i][0] = weightRes[m_index_2[c_i]][0];
405  for(int c_j = 0; c_j < 2; ++c_j)
406  {
407  invCovMB4[c_i][c_j] = invCov[m_index_2[c_i]][m_index_2[c_j]];
408  }
409  }
410  this->updateInfo(invCovMB4, weightResMB4, residuals, chamId);
411  }
412  else
413  {
414  this->updateInfo(invCov, weightRes, residuals, chamId);
415  }*/
416  this->updateInfo(invCov, weightRes, residuals, chamId);
417  }
418  }
419  itsos++;
420  ihit++;
421  }
422  }
423  } // end of track loop
424 }
425 
426 //Auxiliar
428  //for(int i = 0; i < m.num_row(); ++i)
429  // {
430  // for(int j = 0; j < m.num_col(); ++j)
431  // {
432  // std::cout << m[i][j] << " ";
433  // }
434  // std::cout << std::endl;
435  //}
436 }
437 
439  const AlgebraicMatrix &m_weightRes,
440  const AlgebraicMatrix &m_res,
441  std::string id) {
442  std::string id_invCov = id + "_invCov";
443  std::string id_weightRes = id + "_weightRes";
444  std::string id_n = id + "_N";
445 
446  edm::LogInfo("Alignment") << "Entrando";
447 
448  std::map<std::string, AlgebraicMatrix *>::iterator node = map_invCov.find(id_invCov);
449  if (node == map_invCov.end()) {
450  AlgebraicMatrix *f_invCov = new AlgebraicMatrix(m_invCov.num_row(), m_invCov.num_col());
451  AlgebraicMatrix *f_weightRes = new AlgebraicMatrix(m_weightRes.num_row(), m_weightRes.num_col());
452  AlgebraicMatrix *f_n = new AlgebraicMatrix(1, 1);
453 
454  map_invCov.insert(make_pair(id_invCov, f_invCov));
455  map_weightRes.insert(make_pair(id_weightRes, f_weightRes));
456  map_N.insert(make_pair(id_n, f_n));
457 
458  for (int iCount = 0; iCount < 4; ++iCount) {
459  char name[40];
460  snprintf(name, sizeof(name), "%s_var_%d", id.c_str(), iCount);
461  std::string idName(name);
462  float range = 5.0;
463  //if( iCount == 0 || iCount == 1 ) {
464  // range = 0.01;
465  //}
466  TH1D *histo = fs->make<TH1D>(idName.c_str(), idName.c_str(), 200, -range, range);
467  histoMap.insert(make_pair(idName, histo));
468  }
469  }
470 
471  *map_invCov[id_invCov] = *map_invCov[id_invCov] + m_invCov;
472  *map_weightRes[id_weightRes] = *map_weightRes[id_weightRes] + m_weightRes;
473  (*map_N[id_n])[0][0]++;
474 
475  for (int iCount = 0; iCount < 4; ++iCount) {
476  char name[40];
477  snprintf(name, sizeof(name), "%s_var_%d", id.c_str(), iCount);
478  std::string idName(name);
479  histoMap[idName]->Fill(m_res[iCount][0]);
480  }
481 }
482 
#define LogDebug(id)
std::map< std::string, AlgebraicMatrix * > map_weightRes
std::map< std::string, AlgebraicMatrix * > map_invCov
T getParameter(std::string const &) const
AlignableNavigator * theAlignableDetAccessor
ConstRecHitPointer const & recHit() const
AlignableDetOrUnitPtr alignableFromGeomDet(const GeomDet *geomDet)
Returns AlignableDetOrUnitPtr corresponding to given GeomDet.
double normalizedChi2() const
chi-squared divided by n.d.o.f. (or chi-squared * 1e6 if n.d.o.f. is zero)
Definition: TrackBase.h:572
void initialize(const edm::EventSetup &setup, AlignableTracker *tracker, AlignableMuon *muon, AlignableExtras *extras, AlignmentParameterStore *store) override
Call at beginning of job.
selection
main part
Definition: corrVsCorr.py:100
double phi() const
azimuthal angle of momentum vector
Definition: TrackBase.h:614
T * make(const Args &...args) const
make new ROOT object
Definition: TFileService.h:64
void applyParameters(void)
Obsolete: Use AlignableNavigator::alignableDetFromDetId and alignableFromAlignableDet.
Alignable * alignableFromAlignableDet(const AlignableDetOrUnitPtr &adet) const
Get relevant Alignable from AlignableDet.
AlignmentParameters * alignmentParameters() const
Get the AlignmentParameters.
Definition: Alignable.h:58
edm::Service< TFileService > fs
const ConstTrajTrackPairCollection & trajTrackPairs() const
void toTMat(AlgebraicMatrix *, TMatrixD *)
define event information passed to algorithms
DataContainer const & measurements() const
Definition: Trajectory.h:178
double eta() const
pseudorapidity of momentum vector
Definition: TrackBase.h:617
CLHEP::HepMatrix AlgebraicMatrix
double pt() const
track transverse momentum
Definition: TrackBase.h:602
MuonMillepedeAlgorithm(const edm::ParameterSet &cfg)
Constructor.
ROOT::Math::SVector< double, 5 > AlgebraicVector5
DetId geographicalId() const
The label of this GeomDet.
Definition: GeomDet.h:64
void updateInfo(const AlgebraicMatrix &, const AlgebraicMatrix &, const AlgebraicMatrix &, std::string)
unsigned short numberOfValidHits() const
number of valid hits found
Definition: TrackBase.h:740
TrajectoryStateOnSurface const & forwardPredictedState() const
Access to forward predicted state (from fitter or builder)
CLHEP::HepVector AlgebraicVector
void printM(const AlgebraicMatrix &)
AlignmentParameterStore * theAlignmentParameterStore
CompositeAlignmentParameters selectParameters(const std::vector< AlignableDet * > &alignabledets) const
ROOT::Math::SMatrix< double, 5, 5, ROOT::Math::MatRepSym< double, 5 > > AlgebraicSymMatrix55
bool isValid() const
std::map< std::string, TH1D * > histoMap
virtual void terminate()
Called at end of job (must be implemented in derived class)
std::vector< AlignableDetOrUnitPtr > alignablesFromHits(const std::vector< const TransientTrackingRecHit * > &hitvec)
Returns vector AlignableDetOrUnitPtr for given vector of Hits.
#define DEFINE_EDM_PLUGIN(factory, type, name)
DetId geographicalId() const
bool detAndSubdetInMap(const DetId &detid) const
Given a DetId, returns true if DetIds with this detector and subdetector id are in the map (not neces...
std::map< std::string, AlgebraicMatrix * > map_N
Constructor of the full muon geometry.
Definition: AlignableMuon.h:33
align::Alignables theAlignables
void run(const edm::EventSetup &setup, const EventInfo &eventInfo) override
Run the algorithm.
const align::Alignables & alignables(void) const
get all alignables
virtual AlgebraicMatrix selectedDerivatives(const TrajectoryStateOnSurface &tsos, const AlignableDetOrUnitPtr &alidet) const
std::vector< ConstTrajTrackPair > ConstTrajTrackPairCollection