CMS 3D CMS Logo

/afs/cern.ch/work/a/aaltunda/public/www/CMSSW_5_3_14/src/RecoTracker/TkSeedGenerator/src/FastHelix.cc

Go to the documentation of this file.
00001 #include "RecoTracker/TkSeedGenerator/interface/FastHelix.h"
00002 #include "RecoTracker/TkSeedGenerator/interface/FastLine.h"
00003 #include "TrackingTools/TrajectoryParametrization/interface/GlobalTrajectoryParameters.h"
00004 #include "TrackingTools/TrajectoryParametrization/interface/CurvilinearTrajectoryError.h"
00005 #include "TrackingTools/TrajectoryParametrization/interface/CartesianTrajectoryError.h"
00006 
00007 FreeTrajectoryState FastHelix::stateAtVertex() const {
00008   
00009   if(isValid() && (fabs(tesla0) > 1e-3) && theCircle.rho()<maxRho)
00010     return helixStateAtVertex();
00011   else 
00012     return straightLineStateAtVertex();
00013     
00014 }
00015 
00016 FreeTrajectoryState FastHelix::helixStateAtVertex() const {
00017 
00018   // given the above rho>0.
00019   double rho = theCircle.rho();
00020   //remember (radius rho in cm):
00021   //rho = 
00022   //100. * pt * 
00023   //(10./(3.*MagneticField::inTesla(GlobalPoint(0., 0., 0.)).z()));
00024   
00025   // pt = 0.01 * rho * (0.3*MagneticField::inTesla(GlobalPoint(0.,0.,0.)).z());
00026   double pt = 0.01 * rho * 0.3*tesla0;
00027 
00028   // verify that rho is not toooo large
00029   double dcphi = ((theOuterHit.x()-theCircle.x0())*(theMiddleHit.x()-theCircle.x0()) +
00030                   (theOuterHit.y()-theCircle.y0())*(theMiddleHit.y()-theCircle.y0())
00031                   )/(rho*rho);
00032   if (fabs(dcphi)>=1.) return straightLineStateAtVertex();
00033 
00034   GlobalPoint pMid(theMiddleHit);
00035   GlobalPoint v(theVertex);
00036   
00037   double dydx = 0., dxdy = 0.;
00038   double px = 0., py = 0.;
00039   
00040 
00041   // (py/px)|x=v.x() = (dy/dx)|x=v.x()
00042   //remember:
00043   //y(x) = +-sqrt(rho^2 - (x-x0)^2) + y0 
00044   //y(x) =  sqrt(rho^2 - (x-x0)^2) + y0  if y(x) >= y0 
00045   //y(x) = -sqrt(rho^2 - (x-x0)^2) + y0  if y(x) < y0
00046   //=> (dy/dx) = -(x-x0)/sqrt(Q)  if y(x) >= y0
00047   //   (dy/dx) =  (x-x0)/sqrt(Q)  if y(x) < y0
00048   //with Q = rho^2 - (x-x0)^2
00049   // Check approximate slope to determine whether to use dydx or dxdy
00050   // Choose the one that goes to 0 rather than infinity.
00051   double arg1 = rho*rho - (v.x()-theCircle.x0())*(v.x()-theCircle.x0());
00052   double arg2 = rho*rho - (v.y()-theCircle.y0())*(v.y()-theCircle.y0());
00053   if (arg1<0.0 && arg2<0.0) {
00054     if(fabs(theCircle.n2()) > 0.) {
00055       dydx = -theCircle.n1()/theCircle.n2(); //else px = 0
00056       px = pt/sqrt(1. + dydx*dydx);
00057       py = px*dydx;
00058     } else {
00059       px = 0.;
00060       py = pt;
00061     }
00062   } else if ( arg1>arg2 ) {
00063     if( v.y() > theCircle.y0() )
00064       dydx = -(v.x() - theCircle.x0()) / sqrt(arg1);
00065     else
00066       dydx = (v.x() - theCircle.x0()) / sqrt(arg1);
00067     px = pt/sqrt(1. + dydx*dydx);
00068     py = px*dydx;
00069   } else {
00070     if( v.x() > theCircle.x0() )
00071       dxdy = -(v.y() - theCircle.y0()) / sqrt(arg2);
00072     else
00073       dxdy = (v.y() - theCircle.y0()) / sqrt(arg2);
00074     py = pt/sqrt(1. + dxdy*dxdy);
00075     px = py*dxdy;
00076   }
00077   // check sign with scalar product
00078   if(px*(pMid.x() - v.x()) + py*(pMid.y() - v.y()) < 0.) {
00079     px *= -1.;
00080     py *= -1.;
00081   } 
00082 
00083   //calculate z0, pz
00084   //(z, R*phi) linear relation in a helix
00085   //with R, phi defined as radius and angle w.r.t. centre of circle
00086   //in transverse plane
00087   //pz = pT*(dz/d(R*phi)))
00088   
00089 
00090   // VI 23/01/2012
00091   double dzdrphi = theOuterHit.z() - theMiddleHit.z();
00092   dzdrphi /= rho*acos(dcphi);
00093   double pz = pt*dzdrphi;
00094 
00095   /*
00096   // old crap
00097   FastLine flfit(theOuterHit, theMiddleHit, theCircle.rho());
00098   double dzdrphi2 = -flfit.n1()/flfit.n2();
00099 
00100   //  if (fabs(dzdrphi2-dzdrphi)>1.e-5) 
00101   std::cout << "FastHelix: old,new " << dzdrphi2 <<", " <<  dzdrphi << std::endl; 
00102   */
00103 
00104   //get sign of particle
00105 
00106   /*
00107   TrackCharge q = 
00108     ((theCircle.x0()*py - theCircle.y0()*px) / 
00109      (magvtx.z()) < 0.) ? 
00110     -1 : 1;
00111   */
00112   TrackCharge q = 1;
00113   if (theCircle.x0()*py - theCircle.y0()*px < 0) q =-q;
00114   if (tesla0 < 0.) q =-q;
00115 
00116   //VI
00117   if ( useBasisVertex ) {
00118     return FTS(basisVertex, 
00119                GlobalVector(px, py, pz),
00120                q, 
00121                &(*pSetup)
00122                );
00123   } else {
00124     double z_0 =  theMiddleHit.z();
00125     // assume v is before middleHit (opposite to outer)
00126     double ds = ( (v.x()-theCircle.x0())*(theMiddleHit.x()-theCircle.x0()) +
00127                   (v.y()-theCircle.y0())*(theMiddleHit.y()-theCircle.y0())
00128                   )/(rho*rho);
00129     if (fabs(ds)<1.) {
00130       ds = rho*acos(ds);
00131       z_0 -= ds*dzdrphi;
00132     } else { // line????
00133       z_0 -= std::sqrt((theMiddleHit-v).perp2()/(theOuterHit-theMiddleHit).perp2())*(theOuterHit.z()-theMiddleHit.z());
00134     }
00135     
00136     //double z_old = -flfit.c()/flfit.n2();
00137     // std::cout << "v:xyz, z,old,new " << v << "   " << z_old << " " << z_0 << std::endl;
00138 
00139     return FTS(GlobalPoint(v.x(),v.y(),z_0), 
00140                GlobalVector(px, py, pz),
00141                q, 
00142                &(*pSetup)
00143                );
00144   }
00145   
00146 }
00147 
00148 FreeTrajectoryState FastHelix::straightLineStateAtVertex() const {
00149 
00150   //calculate FTS assuming straight line...
00151 
00152   GlobalPoint pMid(theMiddleHit);
00153   GlobalPoint v(theVertex);
00154 
00155   double dydx = 0.;
00156   double pt = 0., px = 0., py = 0.;
00157   
00158   if(fabs(theCircle.n1()) > 0. || fabs(theCircle.n2()) > 0.)
00159     pt = maxPt  ;// 10 TeV //else no pt
00160   if(fabs(theCircle.n2()) > 0.) {
00161     dydx = -theCircle.n1()/theCircle.n2(); //else px = 0 
00162   }
00163   px = pt/sqrt(1. + dydx*dydx);
00164   py = px*dydx;
00165   // check sign with scalar product
00166   if (px*(pMid.x() - v.x()) + py*(pMid.y() - v.y()) < 0.) {
00167     px *= -1.;
00168     py *= -1.;
00169   } 
00170 
00171   //calculate z_0 and pz at vertex using weighted mean
00172   //z = z(r) = z0 + (dz/dr)*r
00173   //tan(theta) = dr/dz = (dz/dr)^-1
00174   //theta = atan(1./dzdr)
00175   //p = pt/sin(theta)
00176   //pz = p*cos(theta) = pt/tan(theta) 
00177 
00178   FastLine flfit(theOuterHit, theMiddleHit);
00179   double dzdr = -flfit.n1()/flfit.n2();
00180   double pz = pt*dzdr; 
00181   
00182   TrackCharge q = 1;
00183   //VI
00184 
00185   if ( useBasisVertex ) {
00186     return FTS(basisVertex, 
00187                GlobalVector(px, py, pz),
00188                q, 
00189                &(*pSetup)
00190                );
00191   } else {
00192   double z_0 = -flfit.c()/flfit.n2();
00193   return FTS(GlobalPoint(v.x(), v.y(), z_0),
00194              GlobalVector(px, py, pz),
00195              q,
00196              &(*pSetup)
00197              );
00198   }
00199 }