CMS 3D CMS Logo

HelixArbitraryPlaneCrossing2Order.cc
Go to the documentation of this file.
2 
5 
6 #include <cmath>
7 #include <cfloat>
9 
11  const DirectionType& direction,
12  const float curvature,
13  const PropagationDirection propDir) :
14  theX0(point.x()),
15  theY0(point.y()),
16  theZ0(point.z()),
17  theRho(curvature),
18  thePropDir(propDir)
19 {
20  //
21  // Components of direction vector (with correct normalisation)
22  //
23  double px = direction.x();
24  double py = direction.y();
25  double pz = direction.z();
26  double pt2 = px*px+py*py;
27  double p2 = pt2+pz*pz;
28  double pI = 1./sqrt(p2);
29  double ptI = 1./sqrt(pt2);
30  theCosPhi0 = px*ptI;
31  theSinPhi0 = py*ptI;
32  theCosTheta = pz*pI;
33  theSinThetaI = p2*pI*ptI; // (1/(pt/p)) = p/pt = p*ptI and p = p2/p = p2*pI
34 }
35 
36 //
37 // Propagation status and path length to intersection
38 //
39 std::pair<bool,double>
41  //
42  // get local z-vector in global co-ordinates and
43  // distance to starting point
44  //
45  GlobalVector normalToPlane = plane.normalVector();
46  double nPx = normalToPlane.x();
47  double nPy = normalToPlane.y();
48  double nPz = normalToPlane.z();
49  double cP = plane.localZ(GlobalPoint(theX0,theY0,theZ0));
50  //
51  // coefficients of 2nd order equation to obtain intersection point
52  // in approximation (without curvature-related factors).
53  //
54  double ceq1 = theRho*(nPx*theSinPhi0-nPy*theCosPhi0);
55  double ceq2 = nPx*theCosPhi0 + nPy*theSinPhi0 + nPz*theCosTheta*theSinThetaI;
56  double ceq3 = cP;
57  //
58  // Check for degeneration to linear equation (zero
59  // curvature, forward plane or direction perp. to plane)
60  //
61  double dS1,dS2;
62  if likely( std::abs(ceq1)>FLT_MIN ) {
63  double deq1 = ceq2*ceq2;
64  double deq2 = ceq1*ceq3;
65  if ( std::abs(deq1)<FLT_MIN || std::abs(deq2/deq1)>1.e-6 ) {
66  //
67  // Standard solution for quadratic equations
68  //
69  double deq = deq1+2*deq2;
70  if unlikely( deq<0. ) return std::pair<bool,double>(false,0);
71  double ceq = ceq2+std::copysign(std::sqrt(deq),ceq2);
72  dS1 = (ceq/ceq1)*theSinThetaI;
73  dS2 = -2.*(ceq3/ceq)*theSinThetaI;
74  }
75  else {
76  //
77  // Solution by expansion of sqrt(1+deq)
78  //
79  double ceq = (ceq2/ceq1)*theSinThetaI;
80  double deq = deq2/deq1;
81  deq *= (1-0.5*deq);
82  dS1 = -ceq*deq;
83  dS2 = ceq*(2+deq);
84  }
85  }
86  else {
87  //
88  // Special case: linear equation
89  //
90  dS1 = dS2 = -(ceq3/ceq2)*theSinThetaI;
91  }
92  //
93  // Choose and return solution
94  //
95  return solutionByDirection(dS1,dS2);
96 }
97 
98 //
99 // Position after a step of path length s (2nd order)
100 //
103  // use double precision result
105  return PositionType(pos.x(),pos.y(),pos.z());
106 }
107 //
108 // Position after a step of path length s (2nd order) (in double precision)
109 //
112  // based on path length in the transverse plane
113  double st = s/theSinThetaI;
114  return PositionTypeDouble(theX0+(theCosPhi0-(st*0.5*theRho)*theSinPhi0)*st,
115  theY0+(theSinPhi0+(st*0.5*theRho)*theCosPhi0)*st,
117 }
118 //
119 // Direction after a step of path length 2 (2nd order) (in double precision)
120 //
123  // use double precision result
125  return DirectionType(dir.x(),dir.y(),dir.z());
126 }
127 //
128 // Direction after a step of path length 2 (2nd order)
129 //
132  // based on delta phi
133  double dph = s*theRho/theSinThetaI;
135  theSinPhi0+(theCosPhi0-0.5*dph*theSinPhi0)*dph,
137 }
138 //
139 // Choice of solution according to propagation direction
140 //
141 std::pair<bool,double>
143  const double dS2) const {
144  bool valid = false;
145  double path = 0;
146  if ( thePropDir == anyDirection ) {
147  valid = true;
148  path = smallestPathLength(dS1,dS2);
149  }
150  else {
151  // use same logic for both directions (invert if necessary)
152  double propSign = thePropDir==alongMomentum ? 1 : -1;
153  double s1(propSign*dS1);
154  double s2(propSign*dS2);
155  // sort
156  if ( s1 > s2 ) std::swap(s1,s2);
157  // choose solution (if any with positive sign)
158  if ( (s1<0) & (s2>=0) ) {
159  // First solution in backward direction: choose second one.
160  valid = true;
161  path = propSign*s2;
162  }
163  else if ( s1>=0 ) {
164  // First solution in forward direction: choose it (s2 is further away!).
165  valid = true;
166  path = propSign*s1;
167  }
168  }
169  return std::pair<bool,double>(valid,path);
170 }
HelixArbitraryPlaneCrossing2Order(const PositionType &point, const DirectionType &direction, const float curvature, const PropagationDirection propDir=alongMomentum)
T y() const
Cartesian y coordinate.
T x() const
Cartesian x coordinate.
DirectionTypeDouble directionInDouble(double s) const
GlobalVector normalVector() const
Definition: Plane.h:41
Global3DPoint GlobalPoint
Definition: GlobalPoint.h:10
virtual std::pair< bool, double > pathLength(const Plane &)
T y() const
Definition: PV3DBase.h:63
float localZ(const GlobalPoint &gp) const
Definition: Plane.h:45
PropagationDirection
double smallestPathLength(const double firstPathLength, const double secondPathLength) const
Definition: Plane.h:17
float float float z
#define unlikely(x)
T x() const
Cartesian x coordinate.
#define likely(x)
T curvature(T InversePt, const edm::EventSetup &iSetup)
T z() const
Cartesian z coordinate.
void swap(edm::DataFrameContainer &lhs, edm::DataFrameContainer &rhs)
T sqrt(T t)
Definition: SSEVec.h:18
T z() const
Definition: PV3DBase.h:64
Abs< T >::type abs(const T &t)
Definition: Abs.h:22
PositionTypeDouble positionInDouble(double s) const
std::pair< bool, double > solutionByDirection(const double dS1, const double dS2) const
Basic3DVector< float > PositionType
the helix is passed to the constructor and does not appear in the interface
Basic3DVector< float > DirectionType
double p2[4]
Definition: TauolaWrapper.h:90
virtual PositionType position(double s) const
virtual DirectionType direction(double s) const
dbl *** dir
Definition: mlp_gen.cc:35
T x() const
Definition: PV3DBase.h:62
*vegas h *****************************************************used in the default bin number in original ***version of VEGAS is ***a higher bin number might help to derive a more precise ***grade subtle point
Definition: invegas.h:5