Logo ROOT   6.13/01
Reference Guide
PxPyPzM4D.h
Go to the documentation of this file.
1 // @(#)root/mathcore:$Id: 464c29f33a8bbd8462a3e15b7e4c30c6f5b74a30 $
2 // Authors: W. Brown, M. Fischler, L. Moneta 2005
3 
4 /**********************************************************************
5 * *
6 * Copyright (c) 2005 , LCG ROOT MathLib Team *
7 * *
8 * *
9 **********************************************************************/
10 
11 // Header file for class PxPyPzM4D
12 //
13 // Created by: fischler at Wed Jul 20 2005
14 // (starting from PxPyPzM4D by moneta)
15 //
16 // Last update: $Id: 464c29f33a8bbd8462a3e15b7e4c30c6f5b74a30 $
17 //
18 #ifndef ROOT_Math_GenVector_PxPyPzM4D
19 #define ROOT_Math_GenVector_PxPyPzM4D 1
20 
21 #include "Math/GenVector/eta.h"
22 
24 
25 
26 #include <cmath>
27 
28 namespace ROOT {
29 
30 namespace Math {
31 
32 //__________________________________________________________________________________________
33 /**
34  Class describing a 4D coordinate system
35  or momentum-energy vectors stored as (Px, Py, Pz, M).
36  This system is useful to describe ultra-relativistic particles
37  (like electrons at LHC) to avoid numerical errors evaluating the mass
38  when E >>> m
39  The metric used is (-,-,-,+)
40  Spacelike particles (M2 < 0) are described with negative mass values,
41  but in this case m2 must alwasy be less than P2 to preserve a positive value of E2
42 
43  @ingroup GenVector
44 */
45 
46 template <class ScalarType = double>
47 class PxPyPzM4D {
48 
49 public :
50 
51  typedef ScalarType Scalar;
52 
53  // --------- Constructors ---------------
54 
55  /**
56  Default constructor with x=y=z=m=0
57  */
58  PxPyPzM4D() : fX(0.0), fY(0.0), fZ(0.0), fM(0.0) { }
59 
60 
61  /**
62  Constructor from x, y , z , m values
63  */
64  PxPyPzM4D(Scalar px, Scalar py, Scalar pz, Scalar m) :
65  fX(px), fY(py), fZ(pz), fM(m) {
66 
67  if (fM < 0) RestrictNegMass();
68  }
69 
70  /**
71  construct from any 4D coordinate system class
72  implementing X(), Y(), X() and M()
73  */
74  template <class CoordSystem>
75  explicit PxPyPzM4D(const CoordSystem & v) :
76  fX( v.X() ), fY( v.Y() ), fZ( v.Z() ), fM( v.M() )
77  { }
78 
79  // for g++ 3.2 and 3.4 on 32 bits found that the compiler generated copy ctor and assignment are much slower
80  // so we decided to re-implement them ( there is no no need to have them with g++4)
81  /**
82  copy constructor
83  */
84  PxPyPzM4D(const PxPyPzM4D & v) :
85  fX(v.fX), fY(v.fY), fZ(v.fZ), fM(v.fM) { }
86 
87  /**
88  assignment operator
89  */
91  fX = v.fX;
92  fY = v.fY;
93  fZ = v.fZ;
94  fM = v.fM;
95  return *this;
96  }
97 
98 
99  /**
100  construct from any 4D coordinate system class
101  implementing X(), Y(), X() and M()
102  */
103  template <class AnyCoordSystem>
104  PxPyPzM4D & operator = (const AnyCoordSystem & v) {
105  fX = v.X();
106  fY = v.Y();
107  fZ = v.Z();
108  fM = v.M();
109  return *this;
110  }
111 
112  /**
113  Set internal data based on an array of 4 Scalar numbers
114  */
115  void SetCoordinates( const Scalar src[] ) {
116  fX=src[0]; fY=src[1]; fZ=src[2]; fM=src[3];
117  if (fM < 0) RestrictNegMass();
118  }
119 
120  /**
121  get internal data into an array of 4 Scalar numbers
122  */
123  void GetCoordinates( Scalar dest[] ) const
124  { dest[0] = fX; dest[1] = fY; dest[2] = fZ; dest[3] = fM; }
125 
126  /**
127  Set internal data based on 4 Scalar numbers
128  */
129  void SetCoordinates(Scalar px, Scalar py, Scalar pz, Scalar m) {
130  fX=px; fY=py; fZ=pz; fM=m;
131  if (fM < 0) RestrictNegMass();
132  }
133 
134  /**
135  get internal data into 4 Scalar numbers
136  */
137  void GetCoordinates(Scalar& px, Scalar& py, Scalar& pz, Scalar& m) const
138  { px=fX; py=fY; pz=fZ; m=fM;}
139 
140  // --------- Coordinates and Coordinate-like Scalar properties -------------
141 
142  // cartesian (Minkowski)coordinate accessors
143 
144  Scalar Px() const { return fX;}
145  Scalar Py() const { return fY;}
146  Scalar Pz() const { return fZ;}
147  Scalar M() const { return fM; }
148 
149  Scalar X() const { return fX;}
150  Scalar Y() const { return fY;}
151  Scalar Z() const { return fZ;}
152 
153  // other coordinate representation
154  /**
155  Energy
156  */
157  Scalar E() const { return sqrt(E2()); }
158 
159  Scalar T() const { return E();}
160 
161  /**
162  squared magnitude of spatial components
163  */
164  Scalar P2() const { return fX*fX + fY*fY + fZ*fZ; }
165 
166  /**
167  magnitude of spatial components (magnitude of 3-momentum)
168  */
169  Scalar P() const { return sqrt(P2()); }
170  Scalar R() const { return P(); }
171 
172  /**
173  vector magnitude squared (or mass squared)
174  In case of negative mass (spacelike particles return negative values)
175  */
176  Scalar M2() const {
177  return ( fM >= 0 ) ? fM*fM : -fM*fM;
178  }
179  Scalar Mag2() const { return M2(); }
180 
181  Scalar Mag() const { return M(); }
182 
183  /**
184  energy squared
185  */
186  Scalar E2() const {
187  Scalar e2 = P2() + M2();
188  // protect against numerical errors when M2() is negative
189  return e2 > 0 ? e2 : 0;
190  }
191 
192  /**
193  transverse spatial component squared
194  */
195  Scalar Pt2() const { return fX*fX + fY*fY;}
196  Scalar Perp2() const { return Pt2();}
197 
198  /**
199  Transverse spatial component (P_perp or rho)
200  */
201  Scalar Pt() const { return sqrt(Perp2()); }
202  Scalar Perp() const { return Pt();}
203  Scalar Rho() const { return Pt();}
204 
205  /**
206  transverse mass squared
207  */
208  Scalar Mt2() const { return E2() - fZ*fZ; }
209 
210  /**
211  transverse mass
212  */
213  Scalar Mt() const {
214  const Scalar mm = Mt2();
215  if (mm >= 0) {
216  return sqrt(mm);
217  } else {
218  GenVector::Throw ("PxPyPzM4D::Mt() - Tachyonic:\n"
219  " Pz^2 > E^2 so the transverse mass would be imaginary");
220  return -sqrt(-mm);
221  }
222  }
223 
224  /**
225  transverse energy squared
226  */
227  Scalar Et2() const { // is (E^2 * pt ^2) / p^2
228  // but it is faster to form p^2 from pt^2
229  Scalar pt2 = Pt2();
230  return pt2 == 0 ? 0 : E2() * pt2/( pt2 + fZ*fZ );
231  }
232 
233  /**
234  transverse energy
235  */
236  Scalar Et() const {
237  const Scalar etet = Et2();
238  return sqrt(etet);
239  }
240 
241  /**
242  azimuthal angle
243  */
244  Scalar Phi() const { return (fX == 0.0 && fY == 0.0) ? 0.0 : atan2(fY, fX); }
245 
246  /**
247  polar angle
248  */
249  Scalar Theta() const { return (fX == 0.0 && fY == 0.0 && fZ == 0.0) ? 0 : atan2(Pt(), fZ); }
250 
251  /**
252  pseudorapidity
253  */
254  Scalar Eta() const {
255  return Impl::Eta_FromRhoZ ( Pt(), fZ);
256  }
257 
258  // --------- Set Coordinates of this system ---------------
259 
260 
261  /**
262  set X value
263  */
264  void SetPx( Scalar px) {
265  fX = px;
266  }
267  /**
268  set Y value
269  */
270  void SetPy( Scalar py) {
271  fY = py;
272  }
273  /**
274  set Z value
275  */
276  void SetPz( Scalar pz) {
277  fZ = pz;
278  }
279  /**
280  set T value
281  */
282  void SetM( Scalar m) {
283  fM = m;
284  if (fM < 0) RestrictNegMass();
285  }
286 
287  /**
288  set all values
289  */
290  void SetPxPyPzE(Scalar px, Scalar py, Scalar pz, Scalar e);
291 
292  // ------ Manipulations -------------
293 
294  /**
295  negate the 4-vector - Note that the energy cannot be negate (would need an additional data member)
296  therefore negate will work only on the spatial components.
297  One would need to use negate only with vectors having the energy as data members
298  */
299  void Negate( ) {
300  fX = -fX;
301  fY = -fY;
302  fZ = -fZ;
303  GenVector::Throw ("PxPyPzM4D::Negate - cannot negate the energy - can negate only the spatial components");
304  }
305 
306  /**
307  scale coordinate values by a scalar quantity a
308  */
309  void Scale( const Scalar & a) {
310  fX *= a;
311  fY *= a;
312  fZ *= a;
313  fM *= a;
314  }
315 
316 
317  /**
318  Exact equality
319  */
320  bool operator == (const PxPyPzM4D & rhs) const {
321  return fX == rhs.fX && fY == rhs.fY && fZ == rhs.fZ && fM == rhs.fM;
322  }
323  bool operator != (const PxPyPzM4D & rhs) const {return !(operator==(rhs));}
324 
325 
326  // ============= Compatibility section ==================
327 
328  // The following make this coordinate system look enough like a CLHEP
329  // vector that an assignment member template can work with either
330  Scalar x() const { return X(); }
331  Scalar y() const { return Y(); }
332  Scalar z() const { return Z(); }
333  Scalar t() const { return E(); }
334 
335 
336 
337 #if defined(__MAKECINT__) || defined(G__DICTIONARY)
338 
339  // ====== Set member functions for coordinates in other systems =======
340 
341  void SetPt(Scalar pt);
342 
343  void SetEta(Scalar eta);
344 
345  void SetPhi(Scalar phi);
346 
347  void SetE(Scalar t);
348 
349 #endif
350 
351 private:
352 
353  // restrict the value of negative mass to avoid unphysical negative E2 values
354  // M2 must be less than P2 for the tachionic particles - otherwise use positive values
355  inline void RestrictNegMass() {
356  if ( fM >=0 ) return;
357  if ( P2() - fM*fM < 0 ) {
358  GenVector::Throw("PxPyPzM4D::unphysical value of mass, set to closest physical value");
359  fM = - P();
360  }
361  return;
362  }
363 
364 
365  /**
366  (contigous) data containing the coordinate values x,y,z,t
367  */
368 
369  ScalarType fX;
370  ScalarType fY;
371  ScalarType fZ;
372  ScalarType fM;
373 
374 };
375 
376 } // end namespace Math
377 } // end namespace ROOT
378 
379 
380 // move implementations here to avoid circle dependencies
381 
384 
385 namespace ROOT {
386 
387 namespace Math {
388 
389 template <class ScalarType>
391  *this = PxPyPzE4D<Scalar> (px, py, pz, e);
392 }
393 
394 
395 #if defined(__MAKECINT__) || defined(G__DICTIONARY)
396 
397  // ====== Set member functions for coordinates in other systems =======
398 
399  // ====== Set member functions for coordinates in other systems =======
400 
401 template <class ScalarType>
402 inline void PxPyPzM4D<ScalarType>::SetPt(ScalarType pt) {
403  GenVector_exception e("PxPyPzM4D::SetPt() is not supposed to be called");
404  throw e;
405  PtEtaPhiE4D<ScalarType> v(*this); v.SetPt(pt); *this = PxPyPzM4D<ScalarType>(v);
406 }
407 template <class ScalarType>
408 inline void PxPyPzM4D<ScalarType>::SetEta(ScalarType eta) {
409  GenVector_exception e("PxPyPzM4D::SetEta() is not supposed to be called");
410  throw e;
411  PtEtaPhiE4D<ScalarType> v(*this); v.SetEta(eta); *this = PxPyPzM4D<ScalarType>(v);
412 }
413 template <class ScalarType>
414 inline void PxPyPzM4D<ScalarType>::SetPhi(ScalarType phi) {
415  GenVector_exception e("PxPyPzM4D::SetPhi() is not supposed to be called");
416  throw e;
417  PtEtaPhiE4D<ScalarType> v(*this); v.SetPhi(phi); *this = PxPyPzM4D<ScalarType>(v);
418 }
419 template <class ScalarType>
420 inline void PxPyPzM4D<ScalarType>::SetE(ScalarType energy) {
421  GenVector_exception e("PxPyPzM4D::SetE() is not supposed to be called");
422  throw e;
423  PxPyPzE4D<ScalarType> v(*this); v.SetE(energy);
424  *this = PxPyPzM4D<ScalarType>(v);
425 }
426 
427 
428 #endif // endif __MAKE__CINT || G__DICTIONARY
429 
430 } // end namespace Math
431 
432 } // end namespace ROOT
433 
434 
435 
436 #endif // ROOT_Math_GenVector_PxPyPzM4D
Class describing a 4D cylindrical coordinate system using Pt , Phi, Eta and E (or rho...
Definition: PtEtaPhiE4D.h:52
void SetPhi(Scalar phi)
set phi value
Definition: PtEtaPhiE4D.h:266
void GetCoordinates(Scalar dest[]) const
get internal data into an array of 4 Scalar numbers
Definition: PxPyPzM4D.h:123
Scalar Theta() const
polar angle
Definition: PxPyPzM4D.h:249
Namespace for new ROOT classes and functions.
Definition: TFoamSampler.h:19
void GetCoordinates(Scalar &px, Scalar &py, Scalar &pz, Scalar &m) const
get internal data into 4 Scalar numbers
Definition: PxPyPzM4D.h:137
Scalar Px() const
Definition: PxPyPzM4D.h:144
Scalar z() const
Definition: PxPyPzM4D.h:332
Scalar Mt2() const
transverse mass squared
Definition: PxPyPzM4D.h:208
void Scale(const Scalar &a)
scale coordinate values by a scalar quantity a
Definition: PxPyPzM4D.h:309
Scalar Mt() const
transverse mass
Definition: PxPyPzM4D.h:213
void Negate()
negate the 4-vector - Note that the energy cannot be negate (would need an additional data member) th...
Definition: PxPyPzM4D.h:299
PxPyPzM4D(const CoordSystem &v)
construct from any 4D coordinate system class implementing X(), Y(), X() and M()
Definition: PxPyPzM4D.h:75
void SetPy(Scalar py)
set Y value
Definition: PxPyPzM4D.h:270
Scalar Rho() const
Definition: PxPyPzM4D.h:203
void SetM(Scalar m)
set T value
Definition: PxPyPzM4D.h:282
Scalar Y() const
Definition: PxPyPzM4D.h:150
VecExpr< UnaryOp< Sqrt< T >, VecExpr< A, T, D >, T >, T, D > sqrt(const VecExpr< A, T, D > &rhs)
Scalar Pz() const
Definition: PxPyPzM4D.h:146
Scalar T() const
Definition: PxPyPzM4D.h:159
Class describing a 4D cartesian coordinate system (x, y, z, t coordinates) or momentum-energy vectors...
Definition: PxPyPzE4D.h:42
Class describing a 4D coordinate system or momentum-energy vectors stored as (Px, Py...
Definition: PxPyPzM4D.h:47
ScalarType fX
(contigous) data containing the coordinate values x,y,z,t
Definition: PxPyPzM4D.h:369
Scalar E() const
Energy.
Definition: PxPyPzM4D.h:157
Scalar x() const
Definition: PxPyPzM4D.h:330
Scalar Et() const
transverse energy
Definition: PxPyPzM4D.h:236
Scalar M2() const
vector magnitude squared (or mass squared) In case of negative mass (spacelike particles return negat...
Definition: PxPyPzM4D.h:176
bool operator==(const PxPyPzM4D &rhs) const
Exact equality.
Definition: PxPyPzM4D.h:320
PxPyPzM4D()
Default constructor with x=y=z=m=0.
Definition: PxPyPzM4D.h:58
Scalar Eta() const
pseudorapidity
Definition: PxPyPzM4D.h:254
Scalar E2() const
energy squared
Definition: PxPyPzM4D.h:186
bool operator!=(const PxPyPzM4D &rhs) const
Definition: PxPyPzM4D.h:323
Scalar t() const
Definition: PxPyPzM4D.h:333
you should not use this method at all Int_t Int_t Double_t Double_t Double_t Int_t Double_t Double_t Double_t Double_t Int_t m
Definition: TRolke.cxx:637
PxPyPzM4D(const PxPyPzM4D &v)
copy constructor
Definition: PxPyPzM4D.h:84
Scalar Pt2() const
transverse spatial component squared
Definition: PxPyPzM4D.h:195
void SetCoordinates(const Scalar src[])
Set internal data based on an array of 4 Scalar numbers.
Definition: PxPyPzM4D.h:115
void SetPt(Scalar pt)
set Pt value
Definition: PtEtaPhiE4D.h:254
Scalar Et2() const
transverse energy squared
Definition: PxPyPzM4D.h:227
void Throw(const char *)
function throwing exception, by creating internally a GenVector_exception only when needed ...
SVector< double, 2 > v
Definition: Dict.h:5
Scalar y() const
Definition: PxPyPzM4D.h:331
Scalar P() const
magnitude of spatial components (magnitude of 3-momentum)
Definition: PxPyPzM4D.h:169
void SetEta(Scalar eta)
set eta value
Definition: PtEtaPhiE4D.h:260
Scalar Phi() const
azimuthal angle
Definition: PxPyPzM4D.h:244
Scalar Py() const
Definition: PxPyPzM4D.h:145
Scalar Eta_FromRhoZ(Scalar rho, Scalar z)
Calculate eta given rho and zeta.
Definition: eta.h:48
void SetPxPyPzE(Scalar px, Scalar py, Scalar pz, Scalar e)
set all values
Definition: PxPyPzM4D.h:390
Scalar P2() const
squared magnitude of spatial components
Definition: PxPyPzM4D.h:164
Scalar R() const
Definition: PxPyPzM4D.h:170
Scalar Perp() const
Definition: PxPyPzM4D.h:202
double atan2(double, double)
ScalarType Scalar
Definition: PxPyPzM4D.h:51
you should not use this method at all Int_t Int_t Double_t Double_t Double_t e
Definition: TRolke.cxx:630
Namespace for new Math classes and functions.
Scalar Pt() const
Transverse spatial component (P_perp or rho)
Definition: PxPyPzM4D.h:201
Scalar Perp2() const
Definition: PxPyPzM4D.h:196
void SetCoordinates(Scalar px, Scalar py, Scalar pz, Scalar m)
Set internal data based on 4 Scalar numbers.
Definition: PxPyPzM4D.h:129
Scalar X() const
Definition: PxPyPzM4D.h:149
PxPyPzM4D & operator=(const PxPyPzM4D &v)
assignment operator
Definition: PxPyPzM4D.h:90
#define dest(otri, vertexptr)
Definition: triangle.c:1040
void SetPz(Scalar pz)
set Z value
Definition: PxPyPzM4D.h:276
Scalar Mag2() const
Definition: PxPyPzM4D.h:179
void SetPx(Scalar px)
set X value
Definition: PxPyPzM4D.h:264
Scalar M() const
Definition: PxPyPzM4D.h:147
PxPyPzM4D(Scalar px, Scalar py, Scalar pz, Scalar m)
Constructor from x, y , z , m values.
Definition: PxPyPzM4D.h:64
Scalar Z() const
Definition: PxPyPzM4D.h:151
void SetE(Scalar e)
set T value
Definition: PxPyPzE4D.h:253
Scalar Mag() const
Definition: PxPyPzM4D.h:181