dayonetrackfit_module.cc
Go to the documentation of this file.
1 ////////////////////////////////////////////////////////////////////////
2 // Class: dayonetrackfit
3 // Plugin Type: producer (art v3_00_00)
4 // File: dayonetrackfit_module.cc
5 //
6 // copied from tpctrackfit2_module.cc and modified for the day one tracker
7 // need to step in Z and not X and compute track parameters nonlinearly
8 ////////////////////////////////////////////////////////////////////////
9 
17 #include "fhiclcpp/ParameterSet.h"
20 #include "canvas/Persistency/Common/FindManyP.h"
21 
22 #include <memory>
23 #include <set>
24 
25 // ROOT includes
26 
27 #include "TVectorF.h"
28 #include "TMatrix.h"
29 #include "TMath.h"
30 #include "TVector3.h"
31 
32 // GArSoft Includes
38 #include "Reco/TrackPar.h"
39 #include "Reco/tracker2algs.h"
40 #include "Geometry/GeometryGAr.h"
41 
42 #include "Geant4/G4ThreeVector.hh"
43 
44 #include "nug4/MagneticField/MagneticField.h"
45 
46 namespace gar {
47  namespace rec {
48 
50  public:
51  explicit dayonetrackfit(fhicl::ParameterSet const& p);
52  // The compiler-generated destructor is fine for non-base
53  // classes without bare pointers or other resource use.
54 
55  // Plugins should not be copied or assigned.
56  dayonetrackfit(dayonetrackfit const&) = delete;
57  dayonetrackfit(dayonetrackfit&&) = delete;
58  dayonetrackfit& operator=(dayonetrackfit const&) = delete;
60 
61  // Required functions.
62  void produce(art::Event& e) override;
63 
64  private:
65 
66  // Declare member data here.
67 
68  std::string fPatRecLabel; ///< input patrec tracks and associations
69  int fPrintLevel; ///< debug printout: 0: none, 1: just track parameters and residuals, 2: all
70  float fKalCurvStepUncSq; ///< constant uncertainty term on each step of the Kalman fit -- squared, for curvature
71  float fKalPhiStepUncSq; ///< constant uncertainty term on each step of the Kalman fit -- squared, for phi
72  float fKalLambdaStepUncSq; ///< constant uncertainty term on each step of the Kalman fit -- squared, for lambda
73  float fTPCClusterResolYZ; ///< pad size in cm in YZ to determine step size
74  float fTPCClusterResolX; ///< drift direction contribution to determine step size (resolution of a TPCCluster)
75  unsigned int fInitialTPNTPCClusters; ///< number of TPCClusters to use for initial trackpar estimate, if present
76  unsigned int fMinNumTPCClusters; ///< minimum number of TPCClusters to define a track
77  int fDumpTracks; ///< 0: do not print out tracks, 1: print out tracks
78  float fTPCClusterResolYZinFit; ///< TPCCluster resolution parameter to use in fit
79  float fRoadYZinFit; ///< cut in cm for dropping TPCClusters from tracks in fit
80  float fSortTransWeight; ///< for use in the hit sorting algorithm -- transverse distance weight factor
81  float fSortDistBack; ///< for use in the hit sorting algorithm -- how far to go back before raising the distance figure of merit
82  float fMinIonizGapCut; ///< Don't compute dEdx for this dx or larger
83 
84  int KalmanFit( std::vector<TPCCluster> &TPCClusters,
85  std::vector<int> &TPCClusterlist,
86  std::vector<float> &trackparatend,
87  float &chisquared,
88  float &length,
89  float *covmat, // 5x5 covariance matrix
90  std::set<int> &unused_TPCClusters,
91  std::vector<std::pair<float,float>>& dSigdX,
92  std::vector<TVector3>& trajpts);
93 
94  int KalmanFitBothWays(std::vector<gar::rec::TPCCluster> &TPCClusters,
95  TrackPar &trackpar, TrackIoniz &trackions, TrackTrajectory &tracktraj);
96 
97  void updatepar(TVectorF &parvec, float zcur, float xh, float yh, float zh, TVectorF &predstep, float &dlength);
98 
99  };
100 
101 
103  {
104  // Call appropriate produces<>() functions here.
105  // Call appropriate consumes<>() for any products to be retrieved by this module.
106 
107  fPatRecLabel = p.get<std::string>("PatRecLabel","patrec");
108  fPrintLevel = p.get<int>("PrintLevel",0);
109  fMinNumTPCClusters = p.get<unsigned int>("MinNumTPCClusters",20);
110  fKalCurvStepUncSq = p.get<float>("KalCurvStepUncSq",1.0E-9);
111  fKalPhiStepUncSq = p.get<float>("KalPhiStepUncSq",1.0E-9);
112  fKalLambdaStepUncSq = p.get<float>("KalLambdaStepUncSq",1.0E-9);
113  fInitialTPNTPCClusters = p.get<unsigned int>("InitialTPNTPCClusters",100);
114  fDumpTracks = p.get<int>("DumpTracks",0);
115  fTPCClusterResolYZ = p.get<float>("TPCClusterResolYZ",1.0); // TODO -- think about what this value is
116  fTPCClusterResolX = p.get<float>("TPCClusterResolX",0.5); // this is probably much better
117  fTPCClusterResolYZinFit = p.get<float>("TPCClusterResolYZinFit",4.0);
118  fRoadYZinFit = p.get<float>("RoadYZinFit",1.0);
119  fSortTransWeight = p.get<float>("SortTransWeight",0.1);
120  fSortDistBack = p.get<float>("SortDistBack",2.0);
121  fMinIonizGapCut = p.get<float>("MinIonizGapCut",5.0);
122 
123  art::InputTag patrecTag(fPatRecLabel);
124  consumes< std::vector<gar::rec::Track> >(patrecTag);
125  consumes< art::Assns<gar::rec::TPCCluster, gar::rec::Track> >(patrecTag);
126 
127  // probably don't need the vector hits at this point if we have the TPCClusters
128  //consumes< std::vector<gar::rec::VecHit> >(patrecTag);
129  //consumes< art::Assns<gar::rec::VecHit, gar::rec::Track> >(patrecTag);
130 
131  produces< std::vector<gar::rec::Track> >();
132  produces< art::Assns<gar::rec::TPCCluster, gar::rec::Track> >();
133  produces<std::vector<gar::rec::TrackIoniz>>();
134  produces<art::Assns<rec::TrackIoniz, rec::Track>>();
135  produces<std::vector<gar::rec::TrackTrajectory>>();
136  produces<art::Assns<rec::TrackTrajectory, rec::Track>>();
137  }
138 
139 
140 
142  {
143  // output collections
144 
145  std::unique_ptr< std::vector<gar::rec::Track> > trkCol(new std::vector<gar::rec::Track>);
146  std::unique_ptr< art::Assns<gar::rec::TPCCluster,gar::rec::Track> > TPCClusterTrkAssns(new ::art::Assns<gar::rec::TPCCluster,gar::rec::Track>);
147  std::unique_ptr< std::vector<rec::TrackIoniz> > ionCol(new std::vector<rec::TrackIoniz>);
148  std::unique_ptr< art::Assns<rec::TrackIoniz,rec::Track> > ionTrkAssns(new ::art::Assns<rec::TrackIoniz,rec::Track>);
149  std::unique_ptr< std::vector<rec::TrackTrajectory> > trajCol(new std::vector<rec::TrackTrajectory>);
150  std::unique_ptr< art::Assns<rec::TrackTrajectory,rec::Track> > trajTrkAssns(new ::art::Assns<rec::TrackTrajectory,rec::Track>);
151 
152  // inputs
153 
154  auto patrecTrackHandle = e.getValidHandle< std::vector<gar::rec::Track> >(fPatRecLabel);
155  auto const& patrecTracks = *patrecTrackHandle;
156 
157  auto const trackPtrMaker = art::PtrMaker<gar::rec::Track>(e);
158  auto const ionizPtrMaker = art::PtrMaker<rec::TrackIoniz>(e);
159  auto const trajPtrMaker = art::PtrMaker<rec::TrackTrajectory>(e);
160  //auto const TPCClusterPtrMaker = art::PtrMaker<gar::rec::TPCCluster>(e, TPCClusterHandle.id());
161 
163  G4ThreeVector zerovec(0,0,0);
164  G4ThreeVector magfield = magFieldService->FieldAtPoint(zerovec);
165 
167  double xtpccent = geo->TPCXCent();
168  double ytpccent = geo->TPCYCent();
169  double ztpccent = geo->TPCZCent();
170  TVector3 tpccent(xtpccent,ytpccent,ztpccent);
171  TVector3 xhat(1,0,0);
172 
173  const art::FindManyP<gar::rec::TPCCluster> TPCClustersFromPatRecTracks(patrecTrackHandle,e,fPatRecLabel);
174 
175  for (size_t itrack = 0; itrack < patrecTracks.size(); ++itrack)
176  {
177  std::vector<gar::rec::TPCCluster> TPCClusters;
178  for (size_t iTPCCluster=0; iTPCCluster < TPCClustersFromPatRecTracks.at(itrack).size(); ++iTPCCluster)
179  {
180  TPCClusters.push_back(*TPCClustersFromPatRecTracks.at(itrack).at(iTPCCluster)); // make our own local copy of TPCClusters. Maybe we can skip this?
181  }
182  TrackPar trackparams;
183  TrackIoniz trackions;
184  TrackTrajectory tracktraj;
185  if (KalmanFitBothWays(TPCClusters,trackparams,trackions,tracktraj) == 0) // to think about -- unused TPCClusters? Or just ignore them in the fit?
186  {
187  trkCol->push_back(trackparams.CreateTrack());
188  ionCol->push_back(trackions);
189  trajCol->push_back(tracktraj);
190  auto const trackpointer = trackPtrMaker(trkCol->size()-1);
191  auto const ionizpointer = ionizPtrMaker(ionCol->size()-1);
192  auto const trajpointer = trajPtrMaker(trajCol->size()-1);
193  for (size_t iTPCCluster=0; iTPCCluster<TPCClusters.size(); ++iTPCCluster)
194  {
195  TPCClusterTrkAssns->addSingle(TPCClustersFromPatRecTracks.at(itrack).at(iTPCCluster),trackpointer);
196  }
197  ionTrkAssns->addSingle(ionizpointer, trackpointer);
198  trajTrkAssns->addSingle(trajpointer, trackpointer);
199  }
200  }
201 
202  e.put(std::move(trkCol));
203  e.put(std::move(TPCClusterTrkAssns));
204  e.put(std::move(ionCol));
205  e.put(std::move(ionTrkAssns));
206  e.put(std::move(trajCol));
207  e.put(std::move(trajTrkAssns));
208  }
209 
210  int dayonetrackfit::KalmanFitBothWays(std::vector<gar::rec::TPCCluster> &TPCClusters,
211  TrackPar &trackpar, TrackIoniz &trackions, TrackTrajectory &tracktraj)
212 
213  {
214  // variables: x is the independent variable
215  // 0: y
216  // 1: z
217  // 2: curvature
218  // 3: phi
219  // 4: lambda = angle from the cathode plane
220  // 5: x /// added on to the end
221 
222 
223  std::vector<int> hlf;
224  std::vector<int> hlb;
225  float lftmp=0; // need these dummy arguments so we can share code with the patrec sorter
226  float lbtmp=0;
228 
229  std::vector<float> tparend(6);
230  float covmatend[25];
231  float chisqforwards = 0;
232  float lengthforwards = 0;
233  std::set<int> unused_TPCClusters;
234  std::vector<std::pair<float,float>> dSigdXs_FWD;
235  std::vector<TVector3> trajpts_FWD;
236 
237  int retcode = KalmanFit(TPCClusters,hlf,tparend,chisqforwards,lengthforwards,covmatend,unused_TPCClusters,dSigdXs_FWD,trajpts_FWD);
238  if (retcode != 0) return 1;
239 
240  // the "backwards" fit is in decreasing x. Track parameters are at the end of the fit, the other end of the track
241 
242  std::vector<float> tparbeg(6);
243  float covmatbeg[25];
244  float chisqbackwards = 0;
245  float lengthbackwards = 0;
246  std::vector<std::pair<float,float>> dSigdXs_BAK;
247  std::vector<TVector3> trajpts_BAK;
248 
249  retcode = KalmanFit(TPCClusters,hlb,tparbeg,chisqbackwards,lengthbackwards,covmatbeg,unused_TPCClusters,dSigdXs_BAK,trajpts_BAK);
250  if (retcode != 0) return 1;
251 
252  size_t nTPCClusters=0;
253  if (TPCClusters.size()>unused_TPCClusters.size())
254  { nTPCClusters = TPCClusters.size()-unused_TPCClusters.size(); }
255  trackpar.setNTPCClusters(nTPCClusters);
256  trackpar.setTime(0);
257  trackpar.setChisqForwards(chisqforwards);
258  trackpar.setChisqBackwards(chisqbackwards);
259  trackpar.setLengthForwards(lengthforwards);
260  trackpar.setLengthBackwards(lengthbackwards);
261  trackpar.setCovMatBeg(covmatbeg);
262  trackpar.setCovMatEnd(covmatend);
263  trackpar.setTrackParametersBegin(tparbeg.data());
264  trackpar.setXBeg(tparbeg[5]);
265  trackpar.setTrackParametersEnd(tparend.data());
266  trackpar.setXEnd(tparend[5]);
267 
268  trackions.setData(dSigdXs_FWD,dSigdXs_BAK);
269  tracktraj.setData(trajpts_FWD,trajpts_BAK);
270 
271  return 0;
272  }
273 
274  //--------------------------------------------------------------------------------------------------------------
275  //--------------------------------------------------------------------------------------------------------------
276 
277  // KalmanFit does a forwards or backwards Kalman fit using the sorted TPCCluster list
278  // variables: z is the independent variable now, but for backwards compatibility, we still report
279  // track parameters with x as a separate parameter -- nb inside the method we use a different track parameters
280  // for this reason
281 
282  // externally visible track parameters
283 
284  // 0: y
285  // 1: z
286  // 2: curvature
287  // 3: phi
288  // 4: lambda
289 
290  // used inside the method below
291 
292  // 0: y
293  // 1: x
294  // 2: curvature
295  // 3: phi
296  // 4: lambda
297 
298  int dayonetrackfit::KalmanFit( std::vector<TPCCluster> &TPCClusters,
299  std::vector<int> &TPCClusterlist, // sort ordered list
300  std::vector<float> &trackparatend,
301  float &chisquared,
302  float &length,
303  float *covmat, // 5x5 covariance matrix
304  std::set<int> &unused_TPCClusters,
305  std::vector<std::pair<float,float>>& dSigdXs,
306  std::vector<TVector3>& trajpts)
307  {
308 
309  // set some default values in case we return early
310 
311  size_t nTPCClusters = TPCClusterlist.size();
312  chisquared = 0;
313  length = 0;
314  for (size_t i=0; i<5; ++i) trackparatend[i] = 0;
315  for (size_t i=0; i<25; ++i) covmat[i] = 0;
316 
317  float roadsq = fRoadYZinFit*fRoadYZinFit;
318 
319  // estimate curvature, lambda, phi, xpos from the initial track parameters
320  float curvature_init=0.1;
321  float phi_init = 0;
322  float lambda_init = 0;
323  float xpos_init=0;
324  float ypos_init=0;
325  float zpos_init=0;
326  float x_other_end = 0;
327  if ( gar::rec::initial_trackpar_estimate(TPCClusters,
328  TPCClusterlist,
329  curvature_init,
330  lambda_init,
331  phi_init,
332  xpos_init,
333  ypos_init,
334  zpos_init,
335  x_other_end,
337  fPrintLevel) != 0)
338  {
339  //std::cout << "kalman fit failed on initial trackpar estimate" << std::endl;
340  return 1;
341  }
342 
343  // Kalman fitter variables
344 
345  float zpos = zpos_init;
346 
347  TMatrixF P(5,5); // covariance matrix of parameters
348  // fill in initial guesses -- generous uncertainties on first value.
349  P.Zero();
350  P[0][0] = TMath::Sq(1); // initial position uncertainties -- y
351  P[1][1] = TMath::Sq(1); // and x
352  P[2][2] = TMath::Sq(.5); // curvature of zero gets us to infinite momentum, and curvature of 2 is curled up tighter than the pads
353  P[3][3] = TMath::Sq(.5); // phi uncertainty
354  P[4][4] = TMath::Sq(.5); // lambda uncertainty
355 
356  TMatrixF PPred(5,5);
357 
358  // per-step additions to the covariance matrix
359  TMatrixF Q(5,5);
360  Q.Zero();
361  Q[2][2] = fKalCurvStepUncSq; // allow for some curvature uncertainty between points
362  Q[3][3] = fKalPhiStepUncSq; // phi
363  Q[4][4] = fKalLambdaStepUncSq; // lambda
364 
365  // uncertainties on the measured points (big for now)
366  TMatrixF R(2,2);
367  R.Zero();
368  R[0][0] = TMath::Sq(fTPCClusterResolYZinFit); // in cm^2
369  R[1][1] = TMath::Sq(fTPCClusterResolYZinFit); // in cm^2
370 
371  // add the TPCClusters and update the track parameters and uncertainties. Put in additional terms to keep uncertainties from shrinking when
372  // scattering and energy loss can change the track parameters along the way.
373 
374  // F = partial(updatefunc)/partial(parvec). Do the drivatives numerically inside the step
375 
376  TMatrixF F(5,5);
377  TMatrixF FT(5,5);
378  TVectorF parvec(5);
379  parvec[0] = ypos_init;
380  parvec[1] = xpos_init;
381  parvec[2] = curvature_init;
382  parvec[3] = phi_init;
383  parvec[4] = lambda_init;
384  TVectorF predstep(5);
385 
386  TMatrixF H(2,5); // partial(obs)/partial(params)
387  H.Zero();
388  H[0][0] = 1; // y
389  H[1][1] = 1; // x
390  TMatrixF HT(5,2);
391 
392  TVectorF z(2);
393  TVectorF ytilde(2);
394  TVectorF hx(2);
395  TMatrixF S(2,2);
396  TMatrixF K(5,2);
397 
398  TMatrixF I(5,5);
399  I.Zero();
400  for (int i=0;i<5;++i) I[i][i] = 1;
401 
402  for (size_t iTPCCluster=1; iTPCCluster<nTPCClusters; ++iTPCCluster)
403  {
404 
405  float xh = TPCClusters[TPCClusterlist[iTPCCluster]].Position()[0];
406  float yh = TPCClusters[TPCClusterlist[iTPCCluster]].Position()[1];
407  float zh = TPCClusters[TPCClusterlist[iTPCCluster]].Position()[2];
408 
409  if (fPrintLevel > 0)
410  {
411  std::cout << std::endl;
412  std::cout << "Adding a new TPCCluster: " << xh << " " << yh << " " << zh << std::endl;
413  }
414 
415  // for readability
416  float lambda = parvec[4];
417  float slope = TMath::Tan(lambda);
418  if (slope != 0)
419  {
420  slope = 1.0/slope;
421  }
422  else
423  {
424  slope = 1E9;
425  }
426 
427  // look for dx below -- need new Z instead
428 
429  if (fPrintLevel > 0)
430  {
431  std::cout << "z: " << zpos << " adding new hit at z: " << zh << std::endl;
432  std::cout << " Parvec: y " << parvec[0] << " z " << parvec[1] << " c " << parvec[2] << " phi " << parvec[3] << " lambda " << parvec[4] << std::endl;
433  }
434 
435  // update prediction to the plane containing zh
436 
437  float dlength=0;
438  updatepar(parvec,zpos,xh,yh,zh,predstep,dlength);
439 
440  if (fPrintLevel > 1)
441  {
442  std::cout << " Predstep: y " << predstep[0] << " z " << predstep[1] << " c " << predstep[2] << " phi " << predstep[3] << " lambda " << predstep[4] << std::endl;
443  }
444 
445  // calculate F with numerical differentiation
446 
447  F.Zero();
448  TVectorF parvec_plus_dpar(5);
449  TVectorF predstepmod(5);
450  TVectorF derivvec(5);
451  for (size_t ipar=0;ipar<5;++ipar)
452  {
453  float epsilon = 0.001;
454  parvec_plus_dpar = parvec;
455  parvec_plus_dpar[ipar] += epsilon;
456  float dldummy=0;
457  updatepar(parvec_plus_dpar,zpos,xh,yh,zh,predstepmod,dldummy);
458  derivvec = (predstepmod - predstep);
459  derivvec *= (1.0/epsilon);
460  for (size_t jpar=0; jpar<5; ++jpar)
461  {
462  F[jpar][ipar] = derivvec[jpar];
463  }
464  }
465 
466  if (fPrintLevel > 1)
467  {
468  std::cout << "F Matrix: " << std::endl;
469  F.Print();
470  std::cout << "P Matrix: " << std::endl;
471  P.Print();
472  }
473 
474  // equations from the extended Kalman filter
475  FT.Transpose(F);
476  PPred = F*P*FT + Q;
477  if (fPrintLevel > 1)
478  {
479  std::cout << "PPred Matrix: " << std::endl;
480  PPred.Print();
481  }
482 
483  ytilde[0] = yh - predstep[0];
484  ytilde[1] = xh - predstep[1];
485  float ydistsq = ytilde.Norm2Sqr();
486  if (ydistsq > roadsq)
487  {
488  unused_TPCClusters.insert(iTPCCluster);
489  continue;
490  }
491  chisquared += ytilde.Norm2Sqr()/TMath::Sq(fTPCClusterResolYZinFit);
492  if (fPrintLevel > 0)
493  {
494  std::cout << "ytilde (residuals): " << std::endl;
495  ytilde.Print();
496  }
497  if (fPrintLevel > 1)
498  {
499  std::cout << "H Matrix: " << std::endl;
500  H.Print();
501  }
502 
503  HT.Transpose(H);
504  S = H*PPred*HT + R;
505  if (fPrintLevel > 1)
506  {
507  std::cout << "S Matrix: " << std::endl;
508  S.Print();
509  }
510 
511  S.Invert();
512  if (fPrintLevel > 1)
513  {
514  std::cout << "Inverted S Matrix: " << std::endl;
515  S.Print();
516  }
517 
518  K = PPred*HT*S;
519  if (fPrintLevel > 1)
520  {
521  std::cout << "K Matrix: " << std::endl;
522  K.Print();
523  }
524 
525  parvec = predstep + K*ytilde;
526  P = (I-K*H)*PPred;
527  zpos = zh;
528  //std::cout << " Updated xpos: " << xpos << " " << dx << std::endl;
529  trajpts.emplace_back(parvec[1],parvec[0],zpos);
530 
531  length += dlength;
532 
533  // Save the ionization data - skip large gaps from sector boundaries
534  float valSig = TPCClusters[TPCClusterlist[iTPCCluster]].Signal();
535  if (dlength < fMinIonizGapCut)
536  {
537  std::pair pushme = std::make_pair(valSig,dlength);
538  dSigdXs.push_back( pushme );
539  }
540  else
541  // Have to remove the fellow before the large gap, too
542  {
543  if (dSigdXs.size()>0) dSigdXs.pop_back();
544  }
545  }
546 
547  for (size_t i=0; i<5; ++i)
548  {
549  trackparatend[i] = parvec[i];
550  }
551  trackparatend[5] = zpos; // tack this on so we can specify where the track endpoint is
552  if (fPrintLevel > 1)
553  {
554  std::cout << "Track params at end (y, z, curv, phi, lambda) " << trackparatend[0] << " " << trackparatend[1] << " " <<
555  trackparatend[2] << " " << trackparatend[3] <<" " << trackparatend[4] << std::endl;
556  S.Print();
557  }
558 
559  // just for visualization of the initial track parameter guesses.
560  // Comment out when fitting tracks.
561  //trackparatend[0] = ypos_init;
562  //trackparatend[1] = zpos_init;
563  //trackparatend[2] = curvature_init;
564  //trackparatend[3] = phi_init;
565  //trackparatend[4] = lambda_init;
566  //trackparatend[5] = xpos_init;
567 
568  // no covariance matrix yet
569 
570  size_t icov=0;
571  for (size_t i=0; i<5; ++i)
572  {
573  for (size_t j=0; j<5; ++j)
574  {
575  covmat[icov] = P[i][j];
576  }
577  }
578 
579  return 0;
580  }
581 
582  //--------------------------------------------------------------------------------------------------------------
583 
584  // extrapolate a helix using the current helix parameters at parvec to a new hit position, given by z.
585  // ouptut is predstep
586 
587  // 0: y
588  // 1: x
589  // 2: curvature
590  // 3: phi
591  // 4: lambda
592 
593  void dayonetrackfit::updatepar(TVectorF &parvec, float zcur, float xh, float yh, float zh, TVectorF &predstep, float &dlength)
594  {
595 
596  predstep = parvec;
597 
598  // radius and center of the circle
599 
600  float r = 1E4;
601  if (parvec[2] != 0)
602  {
603  r = 1/parvec[2];
604  }
605  float yc = parvec[0] + r*TMath::Cos(parvec[3]);
606  float zc = zcur - r*TMath::Sin(parvec[3]);
607 
608  // two solutions of arcsin, plus any number of 2pi. We could be on
609  // the boundary of a wraparound.
610 
611  float phip1 = TMath::ASin((zh-zc)/r);
612  float phip2 = TMath::Pi() - phip1;
613 
614  // find the solution that's closest to the one suggested by x
615 
616  float tanlambda = TMath::Tan(parvec[4]);
617  if (tanlambda == 0) tanlambda = 1E-4;
618  float phip3 = parvec[3] + (xh-parvec[1])/(r*tanlambda);
619 
620  float dphip1n = (phip1-phip3)/TMath::TwoPi();
621  float niphi1 = nearbyint(dphip1n);
622  float dphip1a = TMath::Abs(dphip1n - niphi1);
623 
624  float dphip2n = (phip2-phip3)/TMath::TwoPi();
625  float niphi2 = nearbyint(dphip2n);
626  float dphip2a = TMath::Abs(dphip2n - niphi2);
627 
628  float phiex=phip1 + niphi1*TMath::TwoPi();
629  if (dphip1a > dphip2a)
630  {
631  phiex = phip2 + niphi2*TMath::TwoPi();
632  }
633 
634  // update predstep to values at this z. Leave curvature and lambda
635  // unchanged
636 
637  predstep[0] = yc - r*TMath::Cos(phiex); // y
638  predstep[1] = parvec[1] + r*tanlambda*(phiex-parvec[3]); // x
639  predstep[3] = phiex;
640 
641  dlength = TMath::Abs( r * (phiex - parvec[3]) / TMath::Cos(parvec[4]) );
642  }
643 
644 
646 
647  } // namespace rec
648 } // namespace gar
void setNTPCClusters(const size_t nTPCClusters)
Definition: TrackPar.cxx:214
void setLengthForwards(const float lengthforwards)
Definition: TrackPar.cxx:251
int fPrintLevel
debug printout: 0: none, 1: just track parameters and residuals, 2: all
void updatepar(TVectorF &parvec, float zcur, float xh, float yh, float zh, TVectorF &predstep, float &dlength)
float fTPCClusterResolYZinFit
TPCCluster resolution parameter to use in fit.
rec
Definition: tracks.py:88
dayonetrackfit(fhicl::ParameterSet const &p)
void setCovMatBeg(const float *covmatbeg)
Definition: TrackPar.cxx:235
std::string string
Definition: nybbler.cc:12
EDProducer(fhicl::ParameterSet const &pset)
Definition: EDProducer.h:20
float fTPCClusterResolX
drift direction contribution to determine step size (resolution of a TPCCluster)
float fMinIonizGapCut
Don&#39;t compute dEdx for this dx or larger.
float fKalPhiStepUncSq
constant uncertainty term on each step of the Kalman fit – squared, for phi
struct vector vector
unsigned int fInitialTPNTPCClusters
number of TPCClusters to use for initial trackpar estimate, if present
std::pair< float, std::string > P
void setLengthBackwards(const float lengthbackwards)
Definition: TrackPar.cxx:256
float fSortTransWeight
for use in the hit sorting algorithm – transverse distance weight factor
void setTrackParametersBegin(const float *tparbeg)
Definition: TrackPar.cxx:219
unsigned int fMinNumTPCClusters
minimum number of TPCClusters to define a track
TH3F * zpos
Definition: doAna.cpp:31
const double e
#define DEFINE_ART_MODULE(klass)
Definition: ModuleMacros.h:67
std::string fPatRecLabel
input patrec tracks and associations
def move(depos, offset)
Definition: depos.py:107
float fSortDistBack
for use in the hit sorting algorithm – how far to go back before raising the distance figure of meri...
float fKalCurvStepUncSq
constant uncertainty term on each step of the Kalman fit – squared, for curvature ...
void setXEnd(const float xend)
Definition: TrackPar.cxx:276
void setTrackParametersEnd(const float *tparend)
Definition: TrackPar.cxx:227
ValidHandle< PROD > getValidHandle(InputTag const &tag) const
Definition: DataViewImpl.h:441
p
Definition: test.py:223
ProductID put(std::unique_ptr< PROD > &&edp, std::string const &instance={})
Definition: DataViewImpl.h:686
void setChisqBackwards(const float chisqbackwards)
Definition: TrackPar.cxx:266
void setData(std::vector< TVector3 > ForwardTrajectory, std::vector< TVector3 > BackwardTrajectory)
gar::rec::Track CreateTrack()
Definition: TrackPar.cxx:292
int KalmanFit(std::vector< TPCCluster > &TPCClusters, std::vector< int > &TPCClusterlist, std::vector< float > &trackparatend, float &chisquared, float &length, float *covmat, std::set< int > &unused_TPCClusters, std::vector< std::pair< float, float >> &dSigdX, std::vector< TVector3 > &trajpts)
int KalmanFitBothWays(std::vector< gar::rec::TPCCluster > &TPCClusters, TrackPar &trackpar, TrackIoniz &trackions, TrackTrajectory &tracktraj)
void produce(art::Event &e) override
General GArSoft Utilities.
void setCovMatEnd(const float *covmatend)
Definition: TrackPar.cxx:243
void sort_TPCClusters_along_track(const std::vector< gar::rec::TPCCluster > &TPCClusters, std::vector< int > &hlf, std::vector< int > &hlb, int printlevel, float &lengthforwards, float &lengthbackwards, float sorttransweight, float sortdistback)
void setXBeg(const float xbeg)
Definition: TrackPar.cxx:271
void setData(std::vector< std::pair< float, float >> dSigdX_FWD, std::vector< std::pair< float, float >> dSigdX_BAK)
Definition: TrackIoniz.cxx:20
int fDumpTracks
0: do not print out tracks, 1: print out tracks
void setChisqForwards(const float chisqforwards)
Definition: TrackPar.cxx:261
float fRoadYZinFit
cut in cm for dropping TPCClusters from tracks in fit
float fTPCClusterResolYZ
pad size in cm in YZ to determine step size
LArSoft geometry interface.
Definition: ChannelGeo.h:16
art framework interface to geometry description
float fKalLambdaStepUncSq
constant uncertainty term on each step of the Kalman fit – squared, for lambda
void setTime(const double time)
Definition: TrackPar.cxx:281
dayonetrackfit & operator=(dayonetrackfit const &)=delete
QTextStream & endl(QTextStream &s)
int initial_trackpar_estimate(const std::vector< gar::rec::TPCCluster > &TPCClusters, std::vector< int > &TPCClusterlist, float &curvature_init, float &lambda_init, float &phi_init, float &xpos, float &ypos, float &zpos, float &x_other_end, unsigned int initialtpnTPCClusters, int printlevel)
Definition: tracker2algs.cxx:8