CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
ReferenceTrajectory.cc
Go to the documentation of this file.
1 // Author : Gero Flucke (based on code by Edmund Widl replacing ORCA's TkReferenceTrack)
2 // date : 2006/09/17
3 // last update: $Date: 2012/12/25 16:42:04 $
4 // by : $Author: innocent $
5 
6 #include <memory>
7 
9 
12 
14 
19 
22 
26 
29 
32 
40 
42 
45 
46 //__________________________________________________________________________________
47 
50  &recHits, bool hitsAreReverse,
51  const MagneticField *magField,
52  MaterialEffects materialEffects,
53  PropagationDirection propDir,
54  double mass,
55  bool useBeamSpot, const reco::BeamSpot &beamSpot)
57  (materialEffects >= brokenLinesCoarse) ? 1 : refTsos.localParameters().mixedFormatVector().kSize,
58  (useBeamSpot == true) ? recHits.size()+1 : recHits.size(),
59  (materialEffects >= brokenLinesCoarse) ?
60  2*((useBeamSpot == true) ? recHits.size()+1 : recHits.size()) :
61  ( (materialEffects == breakPoints) ? 2*((useBeamSpot == true) ? recHits.size()+1 : recHits.size())-2 : 0) ,
62  (materialEffects >= brokenLinesCoarse) ?
63  2*((useBeamSpot == true) ? recHits.size()+1 : recHits.size())-4 :
64  ( (materialEffects == breakPoints) ? 2*((useBeamSpot == true) ? recHits.size()+1 : recHits.size())-2 : 0) )
65 {
66  // no check against magField == 0
67  theParameters = asHepVector<5>( refTsos.localParameters().mixedFormatVector() );
68 
69  if (hitsAreReverse) {
71  fwdRecHits.reserve(recHits.size());
72  for (TransientTrackingRecHit::ConstRecHitContainer::const_reverse_iterator it=recHits.rbegin();
73  it != recHits.rend(); ++it) {
74  fwdRecHits.push_back(*it);
75  }
76  theValidityFlag = this->construct(refTsos, fwdRecHits, mass, materialEffects,
77  propDir, magField,
78  useBeamSpot, beamSpot);
79  } else {
80  theValidityFlag = this->construct(refTsos, recHits, mass, materialEffects,
81  propDir, magField,
82  useBeamSpot, beamSpot);
83  }
84 }
85 
86 
87 //__________________________________________________________________________________
88 
89 ReferenceTrajectory::ReferenceTrajectory( unsigned int nPar, unsigned int nHits,
90  MaterialEffects materialEffects)
92  (materialEffects >= brokenLinesCoarse) ? 1 : nPar,
93  nHits,
94  (materialEffects >= brokenLinesCoarse) ? 2*nHits : ( (materialEffects == breakPoints) ? 2*nHits-2 : 0 ),
95  (materialEffects >= brokenLinesCoarse) ? 2*nHits-4 : ( (materialEffects == breakPoints) ? 2*nHits-2 : 0 ) )
96 {}
97 
98 
99 //__________________________________________________________________________________
100 
103  double mass, MaterialEffects materialEffects,
104  const PropagationDirection propDir,
105  const MagneticField *magField,
106  bool useBeamSpot,
107  const reco::BeamSpot &beamSpot)
108 {
109  TrajectoryStateOnSurface theRefTsos = refTsos;
110 
111  const SurfaceSide surfaceSide = this->surfaceSide(propDir);
112  // auto_ptr to avoid memory leaks in case of not reaching delete at end of method:
113  std::auto_ptr<MaterialEffectsUpdator> aMaterialEffectsUpdator
114  (this->createUpdator(materialEffects, mass));
115  if (!aMaterialEffectsUpdator.get()) return false; // empty auto_ptr
116 
117  AlgebraicMatrix fullJacobian(theParameters.num_row(), theParameters.num_row());
118  std::vector<AlgebraicMatrix> allJacobians;
119  allJacobians.reserve(theNumberOfHits);
120 
122  TrajectoryStateOnSurface previousTsos;
123  AlgebraicSymMatrix previousChangeInCurvature(theParameters.num_row(), 1);
124  std::vector<AlgebraicSymMatrix> allCurvatureChanges;
125  allCurvatureChanges.reserve(theNumberOfHits);
126 
127  const LocalTrajectoryError zeroErrors(0., 0., 0., 0., 0.);
128 
129  std::vector<AlgebraicMatrix> allProjections;
130  allProjections.reserve(theNumberOfHits);
131  std::vector<AlgebraicSymMatrix> allDeltaParameterCovs;
132  allDeltaParameterCovs.reserve(theNumberOfHits);
133 
134  // CHK
135  std::vector<AlgebraicMatrix> allLocalToCurv;
136  allLocalToCurv.reserve(theNumberOfHits);
137  std::vector<double> allSteps;
138  allSteps.reserve(theNumberOfHits);
139  std::vector<AlgebraicMatrix> allCurvlinJacobians;
140  allCurvlinJacobians.reserve(theNumberOfHits);
141 
142  AlgebraicMatrix firstCurvlinJacobian(5, 5, 1);
143 
144  unsigned int iRow = 0;
145 
146  // local storage vector of all rechits (including rechit for beam spot in case it is used)
148 
149  if (useBeamSpot && propDir==alongMomentum) {
150 
151  GlobalPoint bs(beamSpot.x0(), beamSpot.y0(), beamSpot.z0());
152 
153  TrajectoryStateClosestToBeamLine tsctbl(TSCBLBuilderNoMaterial()(*(refTsos.freeState()), beamSpot));
154  if (!tsctbl.isValid()) {
155  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::construct"
156  << "TrajectoryStateClostestToBeamLine invalid. Skip track.";
157  return false;
158  }
159 
160  FreeTrajectoryState pcaFts = tsctbl.trackStateAtPCA();
161  GlobalVector bd(beamSpot.dxdz(), beamSpot.dydz(), 1.0);
162 
163  //propagation FIXME: Should use same propagator everywhere...
164  AnalyticalPropagator propagator(magField);
165  std::pair< TrajectoryStateOnSurface, double > tsosWithPath =
166  propagator.propagateWithPath(pcaFts, refTsos.surface());
167 
168  if (!tsosWithPath.first.isValid()) return false;
169 
170  GlobalVector momDir(pcaFts.momentum());
171  GlobalVector perpDir(bd.cross(momDir));
172  Plane::RotationType rotation(perpDir, bd);
173 
174  BeamSpotGeomDet * bsGeom = new BeamSpotGeomDet(Plane::build(bs, rotation));
175 
176  // There is also a constructor taking the magentic field. Use this one instead?
177  theRefTsos = TrajectoryStateOnSurface(pcaFts, bsGeom->surface());
178 
180  bsGeom,
181  theRefTsos.freeState()->momentum().phi()));
182  allRecHits.push_back(bsRecHit);
183 
184  }
185 
186  // copy all rechits to the local storage vector
187  TransientTrackingRecHit::ConstRecHitContainer::const_iterator itRecHit;
188  for ( itRecHit = recHits.begin(); itRecHit != recHits.end(); ++itRecHit ) {
189  const TransientTrackingRecHit::ConstRecHitPointer &hitPtr = *itRecHit;
190  allRecHits.push_back(hitPtr);
191  }
192 
193  for ( itRecHit = allRecHits.begin(); itRecHit != allRecHits.end(); ++itRecHit ) {
194 
195  const TransientTrackingRecHit::ConstRecHitPointer &hitPtr = *itRecHit;
196  theRecHits.push_back(hitPtr);
197 
198  if (0 == iRow) {
199 
200  // compute the derivatives of the reference-track's parameters w.r.t. the initial ones
201  // derivative of the initial reference-track parameters w.r.t. themselves is of course the identity
202  fullJacobian = AlgebraicMatrix(theParameters.num_row(), theParameters.num_row(), 1);
203  allJacobians.push_back(fullJacobian);
204  theTsosVec.push_back(theRefTsos);
205  const JacobianLocalToCurvilinear startTrafo(hitPtr->det()->surface(), theRefTsos.localParameters(), *magField);
206  const AlgebraicMatrix localToCurvilinear = asHepMatrix<5>(startTrafo.jacobian());
207  if (materialEffects <= breakPoints) {
208  theInnerTrajectoryToCurvilinear = asHepMatrix<5>(startTrafo.jacobian());
210  }
211  allLocalToCurv.push_back(localToCurvilinear);
212  allSteps.push_back(0.);
213  allCurvlinJacobians.push_back(firstCurvlinJacobian);
214 
215  } else {
216 
217  AlgebraicMatrix nextJacobian;
218  AlgebraicMatrix nextCurvlinJacobian;
219  double nextStep = 0.;
220  TrajectoryStateOnSurface nextTsos;
221 
222  if (!this->propagate(previousHitPtr->det()->surface(), previousTsos,
223  hitPtr->det()->surface(), nextTsos,
224  nextJacobian, nextCurvlinJacobian, nextStep, propDir, magField)) {
225  return false; // stop if problem...// no delete aMaterialEffectsUpdator needed
226  }
227 
228  allJacobians.push_back(nextJacobian);
229  fullJacobian = nextJacobian * previousChangeInCurvature * fullJacobian;
230  theTsosVec.push_back(nextTsos);
231 
232  const JacobianLocalToCurvilinear startTrafo(hitPtr->det()->surface(), nextTsos.localParameters(), *magField);
233  const AlgebraicMatrix localToCurvilinear = asHepMatrix<5>(startTrafo.jacobian());
234  allLocalToCurv.push_back(localToCurvilinear);
235  if (nextStep == 0.) {
236  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::construct"
237  << "step 0. from id " << previousHitPtr->geographicalId()
238  << " to " << hitPtr->det()->geographicalId() << ".";
239  // brokenLinesFine will not work, brokenLinesCoarse combines close by layers
240  if (materialEffects == brokenLinesFine) {
241  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::construct" << "Skip track.";
242  return false;
243  }
244  }
245  allSteps.push_back(nextStep);
246  allCurvlinJacobians.push_back(nextCurvlinJacobian);
247 
248  }
249 
250  // take material effects into account. since trajectory-state is constructed with errors equal zero,
251  // the updated state contains only the uncertainties due to interactions in the current layer.
252  const TrajectoryStateOnSurface tmpTsos(theTsosVec.back().localParameters(), zeroErrors,
253  theTsosVec.back().surface(), magField, surfaceSide);
254  const TrajectoryStateOnSurface updatedTsos = aMaterialEffectsUpdator->updateState(tmpTsos, propDir);
255 
256  if ( !updatedTsos.isValid() ) return false;// no delete aMaterialEffectsUpdator needed
257 
258  if ( theTsosVec.back().localParameters().charge() )
259  {
260  previousChangeInCurvature[0][0] = updatedTsos.localParameters().signedInverseMomentum()
261  / theTsosVec.back().localParameters().signedInverseMomentum();
262  }
263 
264  // get multiple-scattering covariance-matrix
265  allDeltaParameterCovs.push_back( asHepMatrix<5>(updatedTsos.localError().matrix()) );
266  allCurvatureChanges.push_back(previousChangeInCurvature);
267 
268  // projection-matrix tsos-parameters -> measurement-coordinates
269  allProjections.push_back(this->getHitProjectionMatrix(hitPtr));
270  // set start-parameters for next propagation. trajectory-state without error
271  // - no error propagation needed here.
272  previousHitPtr = hitPtr;
273  previousTsos = TrajectoryStateOnSurface(updatedTsos.globalParameters(),
274  updatedTsos.surface(), surfaceSide);
275 
276  if (materialEffects < brokenLinesCoarse) {
277  this->fillDerivatives(allProjections.back(), fullJacobian, iRow);
278  }
279 
280  AlgebraicVector mixedLocalParams = asHepVector<5>(theTsosVec.back().localParameters().mixedFormatVector());
281  this->fillTrajectoryPositions(allProjections.back(), mixedLocalParams, iRow);
282  if ( useRecHit( hitPtr ) ) this->fillMeasurementAndError(hitPtr, iRow, updatedTsos);
283 
284  iRow += nMeasPerHit;
285  } // end of loop on hits
286 
287  bool msOK = true;
288  switch (materialEffects) {
289  case none:
290  break;
291  case multipleScattering:
292  case energyLoss:
293  case combined:
294  msOK = this->addMaterialEffectsCov(allJacobians, allProjections, allCurvatureChanges,
295  allDeltaParameterCovs);
296  break;
297  case breakPoints:
298  msOK = this->addMaterialEffectsBp(allJacobians, allProjections, allCurvatureChanges,
299  allDeltaParameterCovs, allLocalToCurv);
300  break;
301  case brokenLinesCoarse:
302  msOK = this->addMaterialEffectsBrl(allProjections, allDeltaParameterCovs, allLocalToCurv,
303  allSteps, refTsos.globalParameters());
304  break;
305  case brokenLinesFine:
306  msOK = this->addMaterialEffectsBrl(allCurvlinJacobians, allProjections, allCurvatureChanges,
307  allDeltaParameterCovs, allLocalToCurv, refTsos.globalParameters());
308  }
309  if (!msOK) return false;
310 
311  if (refTsos.hasError()) {
312  AlgebraicSymMatrix parameterCov = asHepMatrix<5>(refTsos.localError().matrix());
313  AlgebraicMatrix parDeriv;
314  if (theNumberOfVirtualPars>0) {
315  parDeriv = theDerivatives.sub( 1, nMeasPerHit*allJacobians.size(), 1, theParameters.num_row() );
316  } else {
317  parDeriv = theDerivatives;
318  }
319  theTrajectoryPositionCov = parameterCov.similarity(parDeriv);
320  } else {
322  }
323 
324  return true;
325 }
326 
327 //__________________________________________________________________________________
328 
330 ReferenceTrajectory::createUpdator(MaterialEffects materialEffects, double mass) const
331 {
332  switch (materialEffects) {
333  // MultipleScatteringUpdator doesn't change the trajectory-state
334  // during update and can therefore be used if material effects should be ignored:
335  case none:
336  case multipleScattering:
337  return new MultipleScatteringUpdator(mass);
338  case energyLoss:
339  return new EnergyLossUpdator(mass);
340  case combined:
341  return new CombinedMaterialEffectsUpdator(mass);
342  case breakPoints:
343  return new CombinedMaterialEffectsUpdator(mass);
344  case brokenLinesCoarse:
345  case brokenLinesFine:
346  return new CombinedMaterialEffectsUpdator(mass);
347 }
348 
349  return 0;
350 }
351 
352 //__________________________________________________________________________________
353 
354 bool ReferenceTrajectory::propagate(const Plane &previousSurface, const TrajectoryStateOnSurface &previousTsos,
355  const Plane &newSurface, TrajectoryStateOnSurface &newTsos, AlgebraicMatrix &newJacobian,
356  AlgebraicMatrix &newCurvlinJacobian, double &nextStep,
357  const PropagationDirection propDir, const MagneticField *magField) const
358 {
359  // propagate to next layer
363  //AnalyticalPropagator aPropagator(magField, propDir);
364  // Hard coded RungeKutta instead Analytical (avoid bias in TEC), but
365  // work around TrackPropagation/RungeKutta/interface/RKTestPropagator.h and
366  // http://www.parashift.com/c++-faq-lite/strange-inheritance.html#faq-23.9
367  defaultRKPropagator::Product rkprod(magField, propDir); //double tolerance = 5.e-5)
368  Propagator &aPropagator = rkprod.propagator;
369  const std::pair<TrajectoryStateOnSurface, double> tsosWithPath =
370  aPropagator.propagateWithPath(previousTsos, newSurface);
371 
372  // stop if propagation wasn't successful
373  if (!tsosWithPath.first.isValid()) return false;
374 
375  nextStep = tsosWithPath.second;
376  // calculate derivative of reference-track parameters on the actual layer w.r.t. the ones
377  // on the previous layer (both in global coordinates)
378  const AnalyticalCurvilinearJacobian aJacobian(previousTsos.globalParameters(),
379  tsosWithPath.first.globalPosition(),
380  tsosWithPath.first.globalMomentum(),
381  tsosWithPath.second);
382  const AlgebraicMatrix curvilinearJacobian = asHepMatrix<5,5>(aJacobian.jacobian());
383 
384  // jacobian of the track parameters on the previous layer for local->global transformation
385  const JacobianLocalToCurvilinear startTrafo(previousSurface, previousTsos.localParameters(), *magField);
386  const AlgebraicMatrix localToCurvilinear = asHepMatrix<5>(startTrafo.jacobian());
387 
388  // jacobian of the track parameters on the actual layer for global->local transformation
389  const JacobianCurvilinearToLocal endTrafo(newSurface, tsosWithPath.first.localParameters(), *magField);
390  const AlgebraicMatrix curvilinearToLocal = asHepMatrix<5>(endTrafo.jacobian());
391 
392  // compute derivative of reference-track parameters on the actual layer w.r.t. the ones on
393  // the previous layer (both in their local representation)
394  newCurvlinJacobian = curvilinearJacobian;
395  newJacobian = curvilinearToLocal * curvilinearJacobian * localToCurvilinear;
396  newTsos = tsosWithPath.first;
397 
398  return true;
399 }
400 
401 //__________________________________________________________________________________
402 
404  unsigned int iRow,
405  const TrajectoryStateOnSurface &updatedTsos)
406 {
407  // get the measurements and their errors, use information updated with tsos if improving
408  // (GF: Also for measurements or only for errors or do the former not change?)
409  // GF 10/2008: I doubt that it makes sense to update the hit with the tsos here:
410  // That is an analytical extrapolation and not the best guess of the real
411  // track state on the module, but the latter should be better to get the best
412  // hit uncertainty estimate!
413 
414  // FIXME FIXME CLONE
415  auto newHitPtr = hitPtr;
416 // TransientTrackingRecHit::ConstRecHitPointer newHitPtr(hitPtr->canImproveWithTrack() ?
417 // hitPtr->clone(updatedTsos) : hitPtr);
418 
419  const LocalPoint localMeasurement = newHitPtr->localPosition();
420  const LocalError localMeasurementCov = newHitPtr->localPositionError();
421 
422  theMeasurements[iRow] = localMeasurement.x();
423  theMeasurements[iRow+1] = localMeasurement.y();
424  theMeasurementsCov[iRow][iRow] = localMeasurementCov.xx();
425  theMeasurementsCov[iRow][iRow+1] = localMeasurementCov.xy();
426  theMeasurementsCov[iRow+1][iRow+1] = localMeasurementCov.yy();
427  // GF: Should be a loop once the hit dimension is not hardcoded as nMeasPerHit (to be checked):
428  // for (int i = 0; i < hitPtr->dimension(); ++i) {
429  // theMeasurements[iRow+i] = hitPtr->parameters()[i]; // fixme: parameters() is by value!
430  // for (int j = i; j < hitPtr->dimension(); ++j) {
431  // theMeasurementsCov[iRow+i][iRow+j] = hitPtr->parametersError()[i][j];
432  // }
433  // }
434 }
435 
436 //__________________________________________________________________________________
437 
439  const AlgebraicMatrix &fullJacobian,
440  unsigned int iRow)
441 {
442  // derivatives of the local coordinates of the reference track w.r.t. to the inital track-parameters
443  const AlgebraicMatrix projectedJacobian(projection * fullJacobian);
444  for (int i = 0; i < parameters().num_row(); ++i) {
445  theDerivatives[iRow ][i] = projectedJacobian[0][i];
446  theDerivatives[iRow+1][i] = projectedJacobian[1][i];
447  // GF: Should be a loop once the hit dimension is not hardcoded as nMeasPerHit (to be checked):
448  // for (int j = 0; j < projection.num_col(); ++j) {
449  // theDerivatives[iRow+j][i] = projectedJacobian[j][i];
450  // }
451  }
452 }
453 
454 //__________________________________________________________________________________
455 
457  const AlgebraicVector &mixedLocalParams,
458  unsigned int iRow)
459 {
460  // get the local coordinates of the reference trajectory
461  const AlgebraicVector localPosition(projection * mixedLocalParams);
462  theTrajectoryPositions[iRow] = localPosition[0];
463  theTrajectoryPositions[iRow+1] = localPosition[1];
464  // GF: Should be a loop once the hit dimension is not hardcoded as nMeasPerHit (to be checked):
465  // for (int j = 0; j < projection.num_col(); ++j) {
466  // theTrajectoryPositions[iRow+j] = localPosition[j];
467  // }
468 }
469 
470 //__________________________________________________________________________________
471 
472 bool ReferenceTrajectory::addMaterialEffectsCov(const std::vector<AlgebraicMatrix> &allJacobians,
473  const std::vector<AlgebraicMatrix> &allProjections,
474  const std::vector<AlgebraicSymMatrix> &allCurvatureChanges,
475  const std::vector<AlgebraicSymMatrix> &allDeltaParameterCovs)
476 {
477  // the uncertainty due to multiple scattering is 'transferred' to the error matrix of the hits
478 
479  // GF: Needs update once hit dimension is not hardcoded as nMeasPerHit!
480 
481  AlgebraicSymMatrix materialEffectsCov(nMeasPerHit * allJacobians.size(), 0);
482 
483  // additional covariance-matrix of the measurements due to material-effects (single measurement)
484  AlgebraicSymMatrix deltaMaterialEffectsCov;
485 
486  // additional covariance-matrix of the parameters due to material-effects
487  AlgebraicSymMatrix paramMaterialEffectsCov(allDeltaParameterCovs[0]); //initialization
488  // error-propagation to state after energy loss
489  //GFback paramMaterialEffectsCov = paramMaterialEffectsCov.similarity(allCurvatureChanges[0]);
490 
491  AlgebraicMatrix tempParameterCov;
492  AlgebraicMatrix tempMeasurementCov;
493 
494  for (unsigned int k = 1; k < allJacobians.size(); ++k) {
495  // error-propagation to next layer
496  paramMaterialEffectsCov = paramMaterialEffectsCov.similarity(allJacobians[k]);
497 
498  // get dependences for the measurements
499  deltaMaterialEffectsCov = paramMaterialEffectsCov.similarity(allProjections[k]);
500  materialEffectsCov[nMeasPerHit*k ][nMeasPerHit*k ] = deltaMaterialEffectsCov[0][0];
501  materialEffectsCov[nMeasPerHit*k ][nMeasPerHit*k+1] = deltaMaterialEffectsCov[0][1];
502  materialEffectsCov[nMeasPerHit*k+1][nMeasPerHit*k ] = deltaMaterialEffectsCov[1][0];
503  materialEffectsCov[nMeasPerHit*k+1][nMeasPerHit*k+1] = deltaMaterialEffectsCov[1][1];
504 
505  // GFback add uncertainties for the following layers due to scattering at this layer
506  paramMaterialEffectsCov += allDeltaParameterCovs[k];
507  // end GFback
508  tempParameterCov = paramMaterialEffectsCov;
509 
510  // compute "inter-layer-dependencies"
511  for (unsigned int l = k+1; l < allJacobians.size(); ++l) {
512  tempParameterCov = allJacobians[l] * allCurvatureChanges[l] * tempParameterCov;
513  tempMeasurementCov = allProjections[l] * tempParameterCov * allProjections[k].T();
514 
515  materialEffectsCov[nMeasPerHit*l][nMeasPerHit*k] = tempMeasurementCov[0][0];
516  materialEffectsCov[nMeasPerHit*k][nMeasPerHit*l] = tempMeasurementCov[0][0];
517 
518  materialEffectsCov[nMeasPerHit*l][nMeasPerHit*k+1] = tempMeasurementCov[0][1];
519  materialEffectsCov[nMeasPerHit*k+1][nMeasPerHit*l] = tempMeasurementCov[0][1];
520 
521  materialEffectsCov[nMeasPerHit*l+1][nMeasPerHit*k] = tempMeasurementCov[1][0];
522  materialEffectsCov[nMeasPerHit*k][nMeasPerHit*l+1] = tempMeasurementCov[1][0];
523 
524  materialEffectsCov[nMeasPerHit*l+1][nMeasPerHit*k+1] = tempMeasurementCov[1][1];
525  materialEffectsCov[nMeasPerHit*k+1][nMeasPerHit*l+1] = tempMeasurementCov[1][1];
526  }
527  // add uncertainties for the following layers due to scattering at this layer
528  // GFback paramMaterialEffectsCov += allDeltaParameterCovs[k];
529  // error-propagation to state after energy loss
530  paramMaterialEffectsCov = paramMaterialEffectsCov.similarity(allCurvatureChanges[k]);
531 
532  }
533  theMeasurementsCov += materialEffectsCov;
534 
535  return true; // cannot fail
536 }
537 
538 //__________________________________________________________________________________
539 
540 bool ReferenceTrajectory::addMaterialEffectsBp(const std::vector<AlgebraicMatrix> &allJacobians,
541  const std::vector<AlgebraicMatrix> &allProjections,
542  const std::vector<AlgebraicSymMatrix> &allCurvatureChanges,
543  const std::vector<AlgebraicSymMatrix> &allDeltaParameterCovs,
544  const std::vector<AlgebraicMatrix> &allLocalToCurv)
545 {
546 //CHK: add material effects using break points
547  int offsetPar = theNumberOfPars;
548  int offsetMeas = nMeasPerHit * allJacobians.size();
549  int ierr = 0;
550 
551  AlgebraicMatrix tempJacobian;
552  AlgebraicMatrix MSprojection(2,5);
553  MSprojection[0][1] = 1;
554  MSprojection[1][2] = 1;
555  AlgebraicSymMatrix tempMSCov;
556  AlgebraicSymMatrix tempMSCovProj;
557  AlgebraicMatrix tempMSJacProj;
558 
559  for (unsigned int k = 1; k < allJacobians.size(); ++k) {
560 // CHK
561  int kbp = k-1;
562  tempJacobian = allJacobians[k] * allCurvatureChanges[k];
563  tempMSCov = allDeltaParameterCovs[k-1].similarity(allLocalToCurv[k-1]);
564  tempMSCovProj = tempMSCov.similarity(MSprojection);
565  theMeasurementsCov[offsetMeas+nMeasPerHit*kbp ][offsetMeas+nMeasPerHit*kbp ] = tempMSCovProj[0][0];
566  theMeasurementsCov[offsetMeas+nMeasPerHit*kbp+1][offsetMeas+nMeasPerHit*kbp+1]= tempMSCovProj[1][1];
567  theDerivatives[offsetMeas+nMeasPerHit*kbp ][offsetPar+2*kbp ] = 1.0;
568  theDerivatives[offsetMeas+nMeasPerHit*kbp+1][offsetPar+2*kbp+1] = 1.0 ;
569 
570  tempMSJacProj = (allProjections[k] * ( tempJacobian * allLocalToCurv[k-1].inverse(ierr) )) * MSprojection.T();
571  if (ierr) {
572  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBp"
573  << "Inversion 1 for break points failed: " << ierr;
574  return false;
575  }
576  theDerivatives[nMeasPerHit*k ][offsetPar+2*kbp ] = tempMSJacProj[0][0];
577  theDerivatives[nMeasPerHit*k ][offsetPar+2*kbp+1] = tempMSJacProj[0][1];
578  theDerivatives[nMeasPerHit*k+1][offsetPar+2*kbp ] = tempMSJacProj[1][0];
579  theDerivatives[nMeasPerHit*k+1][offsetPar+2*kbp+1] = tempMSJacProj[1][1];
580 
581  for (unsigned int l = k+1; l < allJacobians.size(); ++l) {
582 // CHK
583  int kbp = k-1;
584  tempJacobian = allJacobians[l] * allCurvatureChanges[l] * tempJacobian;
585  tempMSJacProj = (allProjections[l] * ( tempJacobian * allLocalToCurv[k-1].inverse(ierr) )) * MSprojection.T();
586  if (ierr) {
587  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBp"
588  << "Inversion 2 for break points failed: " << ierr;
589  return false;
590  }
591  theDerivatives[nMeasPerHit*l ][offsetPar+2*kbp ] = tempMSJacProj[0][0];
592  theDerivatives[nMeasPerHit*l ][offsetPar+2*kbp+1] = tempMSJacProj[0][1];
593  theDerivatives[nMeasPerHit*l+1][offsetPar+2*kbp ] = tempMSJacProj[1][0];
594  theDerivatives[nMeasPerHit*l+1][offsetPar+2*kbp+1] = tempMSJacProj[1][1];
595 
596  }
597 
598  }
599 
600  return true;
601 }
602 
603 //__________________________________________________________________________________
604 
605 bool ReferenceTrajectory::addMaterialEffectsBrl(const std::vector<AlgebraicMatrix> &allCurvlinJacobians,
606  const std::vector<AlgebraicMatrix> &allProjections,
607  const std::vector<AlgebraicSymMatrix> &allCurvatureChanges,
608  const std::vector<AlgebraicSymMatrix> &allDeltaParameterCovs,
609  const std::vector<AlgebraicMatrix> &allLocalToCurv,
610  const GlobalTrajectoryParameters &gtp)
611 {
612 //CHK: add material effects using broken lines
613 //fine: use exact Jacobians, all detectors
614 //broken lines: pair of offsets (u1,u2) = (xt,yt) (in curvilinear frame (q/p,lambda,phi,xt,yt)) at each layer
615 // scattering angles (alpha1,alpha2) = (cosLambda*dPhi, dLambda) (cosLambda cancels in Chi2)
616 // DU' = (dU'/dU)*DU + (dU'/dAlpha)*DAlpha + (dU'/dQbyp)*DQbyp (propagation of U)
617 // = J*DU + S*DAlpha + d*DQbyp
618 // => DAlpha = S^-1 (DU' - J*DU - d*DQbyp)
619 
620  int offsetPar = theNumberOfPars;
621  int offsetMeas = nMeasPerHit*allCurvlinJacobians.size();
622  int ierr = 0;
623 
624  GlobalVector p = gtp.momentum();
625  double cosLambda = sqrt((p.x()*p.x()+p.y()*p.y())/(p.x()*p.x()+p.y()*p.y()+p.z()*p.z()));
626 
627 // transformations Curvilinear <-> BrokenLines
628  AlgebraicMatrix QbypToCurv(5,1); // dCurv/dQbyp
629  QbypToCurv[0][0] = 1.; // dQbyp/dQbyp
630  AlgebraicMatrix AngleToCurv(5,2); // dCurv/dAlpha
631  AngleToCurv[1][1] = 1.; // dlambda/dalpha2
632  AngleToCurv[2][0] = 1./cosLambda; // dphi/dalpha1
633  AlgebraicMatrix CurvToAngle(2,5); // dAlpha/dCurv
634  CurvToAngle[1][1] = 1.; // dalpha2/dlambda
635  CurvToAngle[0][2] = cosLambda; // dalpha1/dphi
636  AlgebraicMatrix OffsetToCurv(5,2); // dCurv/dU
637  OffsetToCurv[3][0] = 1.; // dxt/du1
638  OffsetToCurv[4][1] = 1.; // dyt/du2
639  AlgebraicMatrix CurvToOffset(2,5); // dU/dCurv
640  CurvToOffset[0][3] = 1.; // du1/dxt
641  CurvToOffset[1][4] = 1.; // du2/dyt
642 
643 // transformations trajectory to components (Qbyp, U1, U2)
644  AlgebraicMatrix TrajToQbyp(1,5);
645  TrajToQbyp[0][0] = 1.;
646  AlgebraicMatrix TrajToOff1(2,5);
647  TrajToOff1[0][1] = 1.;
648  TrajToOff1[1][2] = 1.;
649  AlgebraicMatrix TrajToOff2(2,5);
650  TrajToOff2[0][3] = 1.;
651  TrajToOff2[1][4] = 1.;
652 
653  AlgebraicMatrix JacOffsetToAngleC, JacQbypToAngleC;
654  AlgebraicMatrix JacCurvToOffsetL, JacOffsetToOffsetL, JacAngleToOffsetL, JacQbypToOffsetL, JacOffsetToAngleL;
655  AlgebraicMatrix JacCurvToOffsetN, JacOffsetToOffsetN, JacAngleToOffsetN, JacQbypToOffsetN, JacOffsetToAngleN;
656 
657 // transformation from trajectory to curvilinear parameters
658 
659  JacCurvToOffsetN = CurvToOffset * allCurvlinJacobians[1]; // (dU'/dCurv') * (dCurv'/dCurv) @ 2nd point
660  JacOffsetToOffsetN = JacCurvToOffsetN * OffsetToCurv; // J: (dU'/dU) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dU)
661  JacAngleToOffsetN = JacCurvToOffsetN * AngleToCurv; // S: (dU'/dAlpha) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dAlpha)
662  JacQbypToOffsetN = JacCurvToOffsetN * QbypToCurv; // d: (dU'/dQbyp) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dQbyp)
663  JacOffsetToAngleN = JacAngleToOffsetN.inverse(ierr); // W
664  if (ierr) {
665  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
666  << "Inversion 1 for fine broken lines failed: " << ierr;
667  return false;
668  }
669  JacOffsetToAngleC = -(JacOffsetToAngleN * JacOffsetToOffsetN); // (dAlpha/dU)
670  JacQbypToAngleC = -(JacOffsetToAngleN * JacQbypToOffsetN); // (dAlpha/dQbyp)
671  // (dAlpha/dTraj) = (dAlpha/dQbyp) * (dQbyp/dTraj) + (dAlpha/dU1) * (dU1/dTraj) + (dAlpha/dU2) * (dU2/dTraj)
672  AlgebraicMatrix JacTrajToAngle = JacQbypToAngleC * TrajToQbyp + JacOffsetToAngleC * TrajToOff1 + JacOffsetToAngleN * TrajToOff2;
673  // (dCurv/dTraj) = (dCurv/dQbyp) * (dQbyp/dTraj) + (dCurv/dAlpha) * (dAlpha/dTraj) + (dCurv/dU) * (dU/dTraj)
674  theInnerTrajectoryToCurvilinear = QbypToCurv * TrajToQbyp + AngleToCurv * JacTrajToAngle + OffsetToCurv * TrajToOff1;
675  theInnerLocalToTrajectory = theInnerTrajectoryToCurvilinear.inverse(ierr) * allLocalToCurv[0];
676  if (ierr) {
677  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
678  << "Inversion 2 for fine broken lines failed: " << ierr;
679  return false;
680  }
681 
682  AlgebraicMatrix tempJacobian(allCurvatureChanges[0]);
683  AlgebraicSymMatrix tempMSCov;
684  AlgebraicSymMatrix tempMSCovProj;
685  AlgebraicMatrix tempJacL, tempJacN;
686  AlgebraicMatrix JacOffsetToMeas;
687 
688 // measurements from hits
689  for (unsigned int k = 0; k < allCurvlinJacobians.size(); ++k) {
690 // (dMeas/dU) = (dMeas/dLoc) * (dLoc/dCurv) * (dCurv/dU)
691  JacOffsetToMeas = (allProjections[k] * allLocalToCurv[k].inverse(ierr) ) * OffsetToCurv;
692  if (ierr) {
693  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
694  << "Inversion 3 for fine broken lines failed: " << ierr;
695  return false;
696  }
697  theDerivatives[nMeasPerHit*k ][offsetPar+2*k ] = JacOffsetToMeas[0][0];
698  theDerivatives[nMeasPerHit*k ][offsetPar+2*k+1] = JacOffsetToMeas[0][1];
699  theDerivatives[nMeasPerHit*k+1][offsetPar+2*k ] = JacOffsetToMeas[1][0];
700  theDerivatives[nMeasPerHit*k+1][offsetPar+2*k+1] = JacOffsetToMeas[1][1];
701  }
702 
703 // measurement of MS kink
704  for (unsigned int k = 1; k < allCurvlinJacobians.size()-1; ++k) {
705 // CHK
706  int iMsMeas = k-1;
707  int l = k-1; // last hit
708  int n = k+1; // next hit
709 
710 // amount of multiple scattering in layer k (angular error perp to direction)
711  tempMSCov = allDeltaParameterCovs[k].similarity(allLocalToCurv[k]);
712  tempMSCovProj = tempMSCov.similarity(CurvToAngle);
713  theMeasurementsCov[offsetMeas+nMeasPerHit*iMsMeas ][offsetMeas+nMeasPerHit*iMsMeas ] = tempMSCovProj[1][1];
714  theMeasurementsCov[offsetMeas+nMeasPerHit*iMsMeas+1][offsetMeas+nMeasPerHit*iMsMeas+1] = tempMSCovProj[0][0];
715 
716 // transformation matices for offsets ( l <- k -> n )
717  tempJacL = allCurvlinJacobians[k] * tempJacobian;
718  JacCurvToOffsetL = CurvToOffset * tempJacL.inverse(ierr); // (dU'/dCurv') * (dCurv'/dCurv) @ last point
719 
720  if (ierr) {
721  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
722  << "Inversion 4 for fine broken lines failed: " << ierr;
723  return false;
724  }
725  JacOffsetToOffsetL = JacCurvToOffsetL * OffsetToCurv; // J-: (dU'/dU) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dU)
726  JacAngleToOffsetL = JacCurvToOffsetL * AngleToCurv; // S-: (dU'/dAlpha) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dAlpha)
727  JacQbypToOffsetL = JacCurvToOffsetL * QbypToCurv; // d-: (dU'/dQbyp) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dQbyp)
728  JacOffsetToAngleL =-JacAngleToOffsetL.inverse(ierr); // W-
729  if (ierr) {
730  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
731  << "Inversion 5 for fine broken lines failed: " << ierr;
732  return false;
733  }
734  tempJacobian = tempJacobian * allCurvatureChanges[k];
735  tempJacN = allCurvlinJacobians[n] * tempJacobian;
736  JacCurvToOffsetN = CurvToOffset * tempJacN; // (dU'/dCurv') * (dCurv'/dCurv) @ next point
737  JacOffsetToOffsetN = JacCurvToOffsetN * OffsetToCurv; // J+: (dU'/dU) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dU)
738  JacAngleToOffsetN = JacCurvToOffsetN * AngleToCurv; // S+: (dU'/dAlpha) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dAlpha)
739  JacQbypToOffsetN = JacCurvToOffsetN * QbypToCurv; // d+: (dU'/dQbyp) = (dU'/dCurv') * (dCurv'/dCurv) * (dCurv/dQbyp)
740  JacOffsetToAngleN = JacAngleToOffsetN.inverse(ierr); // W+
741  if (ierr) {
742  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
743  << "Inversion 6 for fine broken lines failed: " << ierr;
744  return false;
745  }
746  JacOffsetToAngleC = -(JacOffsetToAngleL * JacOffsetToOffsetL + JacOffsetToAngleN * JacOffsetToOffsetN);
747  JacQbypToAngleC = -(JacOffsetToAngleL * JacQbypToOffsetL + JacOffsetToAngleN * JacQbypToOffsetN);
748 
749  // bending
750  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][ 0] = JacQbypToAngleC[0][0];
751  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][ 0] = JacQbypToAngleC[1][0];
752  // last layer
753  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*l ] = JacOffsetToAngleL[0][0];
754  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*l+1] = JacOffsetToAngleL[0][1];
755  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*l ] = JacOffsetToAngleL[1][0];
756  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*l+1] = JacOffsetToAngleL[1][1];
757  // current layer
758  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*k ] = JacOffsetToAngleC[0][0];
759  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*k+1] = JacOffsetToAngleC[0][1];
760  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*k ] = JacOffsetToAngleC[1][0];
761  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*k+1] = JacOffsetToAngleC[1][1];
762 
763  // next layer
764  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*n ] = JacOffsetToAngleN[0][0];
765  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*n+1] = JacOffsetToAngleN[0][1];
766  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*n ] = JacOffsetToAngleN[1][0];
767  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*n+1] = JacOffsetToAngleN[1][1];
768 
769  }
770 
771  return true;
772 }
773 
774 //__________________________________________________________________________________
775 
776 bool ReferenceTrajectory::addMaterialEffectsBrl(const std::vector<AlgebraicMatrix> &allProjections,
777  const std::vector<AlgebraicSymMatrix> &allDeltaParameterCovs,
778  const std::vector<AlgebraicMatrix> &allLocalToCurv,
779  const std::vector<double> &allSteps,
780  const GlobalTrajectoryParameters &gtp,
781  const double minStep)
782 {
783 //CHK: add material effects using broken lines
784 //BrokenLinesCoarse: combine close by detectors,
785 // use approximate Jacobians from Steps (limit Qbyp -> 0),
786 // bending only in RPhi (B=(0,0,Bz)), no energy loss correction
787 
788  int offsetPar = theNumberOfPars;
789  int offsetMeas = nMeasPerHit*allSteps.size();
790  int ierr = 0;
791 
792  GlobalVector p = gtp.momentum();
793  double cosLambda = sqrt((p.x()*p.x()+p.y()*p.y())/(p.x()*p.x()+p.y()*p.y()+p.z()*p.z()));
794  double bFac = -gtp.magneticFieldInInverseGeV(gtp.position()).mag();
795 
796  // transformation from trajectory to curvilinear parameters at refTsos
797  double delta (1.0/allSteps[1]);
801  theInnerTrajectoryToCurvilinear[2][0] = -0.5*bFac/delta;
802  theInnerTrajectoryToCurvilinear[2][1] = -delta/cosLambda;
803  theInnerTrajectoryToCurvilinear[2][3] = delta/cosLambda;
806  theInnerLocalToTrajectory = theInnerTrajectoryToCurvilinear.inverse(ierr) * allLocalToCurv[0];
807  if (ierr) {
808  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
809  << "Inversion 1 for coarse broken lines failed: " << ierr;
810  return false;
811  }
812 
813  AlgebraicMatrix CurvToAngle(2,5); // dAlpha/dCurv
814  CurvToAngle[1][1] = 1.; // dalpha2/dlambda
815  CurvToAngle[0][2] = cosLambda; // dalpha1/dphi
816  AlgebraicMatrix OffsetToCurv(5,2); // dCurv/dU
817  OffsetToCurv[3][0] = 1.; // dxt/du1
818  OffsetToCurv[4][1] = 1.; // dyt/du2
819 
820  AlgebraicSymMatrix tempMSCov;
821  AlgebraicSymMatrix tempMSCovProj;
822  AlgebraicMatrix JacOffsetToMeas;
823 
824  // combine closeby detectors into single plane
825  std::vector<unsigned int> first(allSteps.size());
826  std::vector<unsigned int> last (allSteps.size());
827  std::vector<unsigned int> plane(allSteps.size());
828  std::vector<double> sPlane(allSteps.size());
829  unsigned int nPlane = 0;
830  double sTot = 0;
831 
832  for (unsigned int k = 1; k < allSteps.size(); ++k) {
833  sTot += allSteps[k];
834  if (fabs(allSteps[k])>minStep) { nPlane += 1; first[nPlane] = k; }
835  last[nPlane] = k;
836  plane[k] = nPlane;
837  sPlane[nPlane] += sTot;
838  }
839  if (nPlane < 2) return false; // pathological cases: need at least 2 planes
840 
841  theNumberOfVirtualPars = 2*(nPlane+1);
842  theNumberOfVirtualMeas = 2*(nPlane-1);// unsigned underflow for nPlane == 0...
843  for (unsigned int k = 0; k <= nPlane; ++k) { sPlane[k] /= (double) (last[k]-first[k]+1); }
844 
845  // measurements from hits
846  sTot = 0;
847  for (unsigned int k = 0; k < allSteps.size(); ++k) {
848  sTot += allSteps[k];
849 // (dMeas/dU) = (dMeas/dLoc) * (dLoc/dCurv) * (dCurv/dU)
850  JacOffsetToMeas = (allProjections[k] * allLocalToCurv[k].inverse(ierr) ) * OffsetToCurv;
851  if (ierr) {
852  edm::LogError("Alignment") << "@SUB=ReferenceTrajectory::addMaterialEffectsBrl"
853  << "Inversion 2 for coarse broken lines failed: " << ierr;
854  return false;
855  }
856 
857  unsigned int iPlane = plane[k];
858  if (last[iPlane] == first[iPlane])
859  { // single plane
860  theDerivatives[nMeasPerHit*k ][offsetPar+2*iPlane ] = JacOffsetToMeas[0][0];
861  theDerivatives[nMeasPerHit*k ][offsetPar+2*iPlane+1] = JacOffsetToMeas[0][1];
862  theDerivatives[nMeasPerHit*k+1][offsetPar+2*iPlane ] = JacOffsetToMeas[1][0];
863  theDerivatives[nMeasPerHit*k+1][offsetPar+2*iPlane+1] = JacOffsetToMeas[1][1];
864  } else
865  { // combined plane: (linear) interpolation
866  unsigned int jPlane; // neighbor plane for interpolation
867  if (fabs(sTot) < fabs(sPlane[iPlane])) { jPlane = (iPlane>0) ? iPlane - 1 : 1; }
868  else { jPlane = (iPlane<nPlane) ? iPlane + 1 : nPlane -1 ;}
869  // interpolation weights
870  double sDiff = sPlane[iPlane] - sPlane[jPlane];
871  double iFrac = (sTot - sPlane[jPlane]) / sDiff;
872  double jFrac = 1.0 - iFrac;
873  theDerivatives[nMeasPerHit*k ][offsetPar+2*iPlane ] = JacOffsetToMeas[0][0]*iFrac;
874  theDerivatives[nMeasPerHit*k ][offsetPar+2*iPlane+1] = JacOffsetToMeas[0][1]*iFrac;
875  theDerivatives[nMeasPerHit*k+1][offsetPar+2*iPlane ] = JacOffsetToMeas[1][0]*iFrac;
876  theDerivatives[nMeasPerHit*k+1][offsetPar+2*iPlane+1] = JacOffsetToMeas[1][1]*iFrac;
877  theDerivatives[nMeasPerHit*k ][offsetPar+2*jPlane ] = JacOffsetToMeas[0][0]*jFrac;
878  theDerivatives[nMeasPerHit*k ][offsetPar+2*jPlane+1] = JacOffsetToMeas[0][1]*jFrac;
879  theDerivatives[nMeasPerHit*k+1][offsetPar+2*jPlane ] = JacOffsetToMeas[1][0]*jFrac;
880  theDerivatives[nMeasPerHit*k+1][offsetPar+2*jPlane+1] = JacOffsetToMeas[1][1]*jFrac;
881  // 2nd order neglected
882  // theDerivatives[nMeasPerHit*k ][ 0] = -0.5*bFac*sDiff*iFrac*sDiff*jFrac*cosLambda;
883  }
884  }
885 
886 // measurement of MS kink
887  for (unsigned int i = 1; i < nPlane; ++i) {
888 // CHK
889  int iMsMeas = i-1;
890  int l = i-1; // last hit
891  int n = i+1; // next hit
892 
893 // amount of multiple scattering in plane k
894  for (unsigned int k = first[i]; k <= last[i]; ++k) {
895  tempMSCov = allDeltaParameterCovs[k].similarity(allLocalToCurv[k]);
896  tempMSCovProj = tempMSCov.similarity(CurvToAngle);
897  theMeasurementsCov[offsetMeas+nMeasPerHit*iMsMeas ][offsetMeas+nMeasPerHit*iMsMeas ] += tempMSCovProj[0][0];
898  theMeasurementsCov[offsetMeas+nMeasPerHit*iMsMeas+1][offsetMeas+nMeasPerHit*iMsMeas+1] += tempMSCovProj[1][1];
899  }
900 // broken line measurements for layer k, correlations between both planes neglected
901  double stepK = sPlane[i] - sPlane[l];
902  double stepN = sPlane[n] - sPlane[i];
903  double deltaK (1.0/stepK);
904  double deltaN (1.0/stepN);
905  // bending (only in RPhi)
906  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][ 0] = -0.5*bFac*(stepK+stepN)*cosLambda;
907  // last layer
908  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*l ] = deltaK;
909  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*l+1] = deltaK;
910  // current layer
911  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*i ] = -(deltaK + deltaN);
912  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*i+1] = -(deltaK + deltaN);
913  // next layer
914  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas ][offsetPar+2*n ] = deltaN;
915  theDerivatives[offsetMeas+nMeasPerHit*iMsMeas+1][offsetPar+2*n+1] = deltaN;
916  }
917 
918  return true;
919 }
920 
921 //__________________________________________________________________________________
922 
926 {
927  if (this->useRecHit(hitPtr)) {
928  // check which templated non-member function to call:
929  switch (hitPtr->dimension()) {
930  case 1:
931  return getHitProjectionMatrixT<1>(hitPtr);
932  case 2:
933  return getHitProjectionMatrixT<2>(hitPtr);
934  case 3:
935  return getHitProjectionMatrixT<3>(hitPtr);
936  case 4:
937  return getHitProjectionMatrixT<4>(hitPtr);
938  case 5:
939  return getHitProjectionMatrixT<5>(hitPtr);
940  default:
941  throw cms::Exception("ReferenceTrajectory::getHitProjectionMatrix")
942  << "Unexpected hit dimension: " << hitPtr->dimension() << "\n";
943  }
944  }
945  // invalid or (to please compiler) unknown dimension
946  return AlgebraicMatrix(2, 5, 0); // get size from ???
947 }
948 
949 //__________________________________________________________________________________
950 
951 template<unsigned int N>
955 {
956  // define variables that will be used to setup the KfComponentsHolder
957  // (their allocated memory is needed by 'hitPtr->getKfComponents(..)'
958  // ProjectMatrix<double,5,N> pf; // not needed
960  typename AlgebraicROOTObject<N>::Vector r, rMeas;
961  typename AlgebraicROOTObject<N,N>::SymMatrix V, VMeas;
962  // input for the holder - but dummy is OK here to just get the projection matrix:
963  const AlgebraicVector5 dummyPars;
964  const AlgebraicSymMatrix55 dummyErr;
965  ProjectMatrix<double,5,N> dummyProjFunc;
966 
967  // setup the holder with the correct dimensions and get the values
968  KfComponentsHolder holder;
969  holder.setup<N>(&r, &V, &H, &dummyProjFunc, &rMeas, &VMeas, dummyPars, dummyErr);
970  hitPtr->getKfComponents(holder);
971 
972  return asHepMatrix<N,5>(holder.projection<N>());
973 }
974 
dbl * delta
Definition: mlp_gen.cc:36
AlgebraicMatrix theInnerTrajectoryToCurvilinear
double z0() const
z coordinate
Definition: BeamSpot.h:68
int i
Definition: DBlmapReader.cc:9
float xx() const
Definition: LocalError.h:24
AlgebraicMatrix getHitProjectionMatrix(const TransientTrackingRecHit::ConstRecHitPointer &recHit) const
ROOT::Math::SMatrix< double, D1, D1, ROOT::Math::MatRepSym< double, D1 > > SymMatrix
virtual bool addMaterialEffectsBrl(const std::vector< AlgebraicMatrix > &allJacobians, const std::vector< AlgebraicMatrix > &allProjections, const std::vector< AlgebraicSymMatrix > &allCurvChanges, const std::vector< AlgebraicSymMatrix > &allDeltaParaCovs, const std::vector< AlgebraicMatrix > &allLocalToCurv, const GlobalTrajectoryParameters &gtp)
const LocalTrajectoryParameters & localParameters() const
virtual bool construct(const TrajectoryStateOnSurface &referenceTsos, const TransientTrackingRecHit::ConstRecHitContainer &recHits, double mass, MaterialEffects materialEffects, const PropagationDirection propDir, const MagneticField *magField, bool useBeamSpot, const reco::BeamSpot &beamSpot)
AlgebraicMatrix theInnerLocalToTrajectory
virtual void fillMeasurementAndError(const TransientTrackingRecHit::ConstRecHitPointer &hitPtr, unsigned int iRow, const TrajectoryStateOnSurface &updatedTsos)
static const unsigned int nMeasPerHit
T mag() const
The vector magnitude. Equivalent to sqrt(vec.mag2())
Geom::Phi< T > phi() const
Definition: PV3DBase.h:69
T y() const
Definition: PV3DBase.h:63
ROOT::Math::SMatrix< double, 5, 5, ROOT::Math::MatRepSym< double, 5 > > AlgebraicSymMatrix55
PropagationDirection
SurfaceSide surfaceSide(const PropagationDirection dir) const
virtual bool addMaterialEffectsBp(const std::vector< AlgebraicMatrix > &allJacobians, const std::vector< AlgebraicMatrix > &allProjections, const std::vector< AlgebraicSymMatrix > &allCurvChanges, const std::vector< AlgebraicSymMatrix > &allDeltaParaCovs, const std::vector< AlgebraicMatrix > &allLocalToCurv)
GlobalVector magneticFieldInInverseGeV(const GlobalPoint &x) const
const Plane & surface() const
The nominal surface of the GeomDet.
Definition: GeomDet.h:35
Definition: Plane.h:17
std::pair< TrajectoryStateOnSurface, double > propagateWithPath(const FreeTrajectoryState &fts, const Plane &plane) const override
propagation to plane with path length
virtual bool propagate(const Plane &previousSurface, const TrajectoryStateOnSurface &previousTsos, const Plane &newSurface, TrajectoryStateOnSurface &newTsos, AlgebraicMatrix &newJacobian, AlgebraicMatrix &newCurvlinJacobian, double &nextStep, const PropagationDirection propDir, const MagneticField *magField) const
AlgebraicSymMatrix theTrajectoryPositionCov
double dydz() const
dydz slope
Definition: BeamSpot.h:84
ROOT::Math::SMatrix< double, D1, D2, ROOT::Math::MatRepStd< double, D1, D2 > > Matrix
float xy() const
Definition: LocalError.h:25
const SurfaceType & surface() const
CLHEP::HepMatrix AlgebraicMatrix
float yy() const
Definition: LocalError.h:26
std::shared_ptr< TrackingRecHit const > ConstRecHitPointer
T sqrt(T t)
Definition: SSEVec.h:48
ReferenceTrajectory(const TrajectoryStateOnSurface &referenceTsos, const TransientTrackingRecHit::ConstRecHitContainer &recHits, bool hitsAreReverse, const MagneticField *magField, MaterialEffects materialEffects, PropagationDirection propDir, double mass, bool useBeamSpot, const reco::BeamSpot &beamSpot)
FreeTrajectoryState const * freeState(bool withErrors=true) const
Vector3DBase< typename PreciseFloatType< T, U >::Type, FrameTag > cross(const Vector3DBase< U, FrameTag > &v) const
Definition: Vector3DBase.h:119
T z() const
Definition: PV3DBase.h:64
MaterialEffectsUpdator * createUpdator(MaterialEffects materialEffects, double mass) const
void setup(typename AlgebraicROOTObject< D >::Vector *params, typename AlgebraicROOTObject< D, D >::SymMatrix *errors, typename AlgebraicROOTObject< D, 5 >::Matrix *projection, ProjectMatrix< double, 5, D > *projFunc, typename AlgebraicROOTObject< D >::Vector *measuredParams, typename AlgebraicROOTObject< D, D >::SymMatrix *measuredErrors, const AlgebraicVector5 &tsosLocalParameters, const AlgebraicSymMatrix55 &tsosLocalErrors)
const AlgebraicSymMatrix55 & matrix() const
virtual void fillDerivatives(const AlgebraicMatrix &projection, const AlgebraicMatrix &fullJacobian, unsigned int iRow)
const LocalTrajectoryError & localError() const
bool first
Definition: L1TdeRCT.cc:75
virtual std::pair< TrajectoryStateOnSurface, double > propagateWithPath(const FreeTrajectoryState &, const Surface &) const final
Definition: Propagator.cc:15
GlobalVector momentum() const
double dxdz() const
dxdz slope
Definition: BeamSpot.h:82
TransientTrackingRecHit::ConstRecHitContainer theRecHits
std::vector< ConstRecHitPointer > ConstRecHitContainer
int k[5][pyjets_maxn]
AlgebraicSymMatrix theMeasurementsCov
AlgebraicMatrix getHitProjectionMatrixT(const TransientTrackingRecHit::ConstRecHitPointer &recHit) const
const AlgebraicVector & parameters() const
CLHEP::HepVector AlgebraicVector
ROOT::Math::SVector< double, D1 > Vector
#define N
Definition: blowfish.cc:9
ROOT::Math::SVector< double, 5 > AlgebraicVector5
const GlobalTrajectoryParameters & globalParameters() const
AlgebraicVector5 mixedFormatVector() const
CLHEP::HepSymMatrix AlgebraicSymMatrix
std::vector< TrajectoryStateOnSurface > theTsosVec
double y0() const
y coordinate
Definition: BeamSpot.h:66
virtual bool addMaterialEffectsCov(const std::vector< AlgebraicMatrix > &allJacobians, const std::vector< AlgebraicMatrix > &allProjections, const std::vector< AlgebraicSymMatrix > &allCurvChanges, const std::vector< AlgebraicSymMatrix > &allDeltaParaCovs)
virtual void fillTrajectoryPositions(const AlgebraicMatrix &projection, const AlgebraicVector &mixedLocalParams, unsigned int iRow)
bool useRecHit(const TransientTrackingRecHit::ConstRecHitPointer &hitPtr) const
AlgebraicROOTObject< D, 5 >::Matrix & projection()
T x() const
Definition: PV3DBase.h:62
double signedInverseMomentum() const
Signed inverse momentum q/p (zero for neutrals).
tuple size
Write out results.
double x0() const
x coordinate
Definition: BeamSpot.h:64