Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-12-15 10:28:10

0001 // @(#)root/mathcore:$Id$
0002 // Authors: W. Brown, M. Fischler, L. Moneta    2005
0003 
0004  /**********************************************************************
0005   *                                                                    *
0006   * Copyright (c) 2005 , LCG ROOT MathLib Team  and                    *
0007   *                                                                    *
0008   *                                                                    *
0009   **********************************************************************/
0010 
0011 // Header file for class Cylindrica3D
0012 //
0013 // Created by: Lorenzo Moneta  at Tue Dec 06 2005
0014 //
0015 //
0016 #ifndef ROOT_Math_GenVector_Cylindrical3D
0017 #define ROOT_Math_GenVector_Cylindrical3D  1
0018 
0019 #include "TMath.h"
0020 
0021 #include "Math/GenVector/eta.h"
0022 
0023 #include <limits>
0024 #include <cmath>
0025 
0026 namespace ROOT {
0027 
0028 namespace Math {
0029 
0030 //__________________________________________________________________________________________
0031   /**
0032       Class describing a cylindrical coordinate system based on rho, z and phi.
0033       The base coordinates are rho (transverse component) , z and phi
0034       Phi is restricted to be in the range [-PI,PI)
0035 
0036       @ingroup GenVector
0037 
0038       @see GenVector
0039   */
0040 
0041 template <class T>
0042 class Cylindrical3D {
0043 
0044 public :
0045 
0046    typedef T Scalar;
0047    static constexpr unsigned int Dimension = 3U;
0048 
0049    /**
0050       Default constructor with rho=z=phi=0
0051    */
0052    constexpr Cylindrical3D() noexcept = default;
0053 
0054    /**
0055       Construct from rho eta and phi values
0056    */
0057    constexpr Cylindrical3D(Scalar rho, Scalar zz, Scalar phi) noexcept : fRho(rho), fZ(zz), fPhi(phi) { Restrict(); }
0058 
0059    /**
0060       Construct from any Vector or coordinate system implementing
0061       Rho(), Z() and Phi()
0062    */
0063    template <class CoordSystem >
0064    explicit constexpr Cylindrical3D( const CoordSystem & v ) :
0065       fRho( v.Rho() ),  fZ( v.Z() ),  fPhi( v.Phi() ) { Restrict(); }
0066 
0067    /**
0068       Set internal data based on an array of 3 Scalar numbers ( rho, z , phi)
0069    */
0070    void SetCoordinates( const Scalar src[] )
0071    { fRho=src[0]; fZ=src[1]; fPhi=src[2]; Restrict(); }
0072 
0073    /**
0074       get internal data into an array of 3 Scalar numbers ( rho, z , phi)
0075    */
0076    void GetCoordinates( Scalar dest[] ) const
0077    { dest[0] = fRho; dest[1] = fZ; dest[2] = fPhi; }
0078 
0079    /**
0080       Set internal data based on 3 Scalar numbers ( rho, z , phi)
0081    */
0082    void SetCoordinates(Scalar  rho, Scalar  zz, Scalar  phi)
0083    { fRho=rho; fZ=zz; fPhi=phi; Restrict(); }
0084 
0085    /**
0086       get internal data into 3 Scalar numbers ( rho, z , phi)
0087    */
0088    void GetCoordinates(Scalar& rho, Scalar& zz, Scalar& phi) const
0089    {rho=fRho; zz=fZ; phi=fPhi;}
0090 
0091 private:
0092    inline static Scalar pi() { return Scalar(TMath::Pi()); }
0093    inline void          Restrict()
0094    {
0095       using std::floor;
0096       if (fPhi <= -pi() || fPhi > pi()) fPhi = fPhi - floor(fPhi / (2 * pi()) + .5) * 2 * pi();
0097    }
0098 public:
0099 
0100    // accessors
0101 
0102    Scalar Rho()   const { return fRho; }
0103    Scalar Z()     const { return fZ;   }
0104    Scalar Phi()   const { return fPhi; }
0105    Scalar X() const { using std::cos; return fRho * cos(fPhi); }
0106    Scalar Y() const { using std::sin; return fRho * sin(fPhi); }
0107 
0108    Scalar Mag2()  const { return fRho*fRho + fZ*fZ;   }
0109    Scalar R() const { using std::sqrt; return sqrt(Mag2()); }
0110    Scalar Perp2() const { return fRho*fRho;           }
0111    Scalar Theta() const { using std::atan2; return (fRho == Scalar(0) && fZ == Scalar(0)) ? Scalar(0) : atan2(fRho, fZ); }
0112 
0113    // pseudorapidity - use same implementation as in Cartesian3D
0114    Scalar Eta() const {
0115       return Impl::Eta_FromRhoZ( fRho, fZ);
0116    }
0117 
0118    // setters (only for data members)
0119 
0120 
0121    /**
0122        set the rho coordinate value keeping z and phi constant
0123    */
0124    void SetRho(T rho) {
0125       fRho = rho;
0126    }
0127 
0128    /**
0129        set the z coordinate value keeping rho and phi constant
0130    */
0131    void SetZ(T zz) {
0132       fZ = zz;
0133    }
0134 
0135    /**
0136        set the phi coordinate value keeping rho and z constant
0137    */
0138    void SetPhi(T phi) {
0139       fPhi = phi;
0140       Restrict();
0141    }
0142 
0143    /**
0144        set all values using cartesian coordinates
0145    */
0146    void SetXYZ(Scalar x, Scalar y, Scalar z);
0147 
0148    /**
0149       scale by a scalar quantity a --
0150       for cylindrical coords only rho and z change
0151    */
0152    void Scale (T a) {
0153       if (a < 0) {
0154          Negate();
0155          a = -a;
0156       }
0157       fRho *= a;
0158       fZ *= a;
0159    }
0160 
0161    /**
0162       negate the vector
0163    */
0164    void Negate ( ) {
0165       fPhi = ( fPhi > 0 ? fPhi - pi() : fPhi + pi() );
0166       fZ = -fZ;
0167    }
0168 
0169    // assignment operators
0170    /**
0171       generic assignment operator from any coordinate system implementing Rho(), Z() and Phi()
0172    */
0173    template <class CoordSystem >
0174    Cylindrical3D & operator= ( const CoordSystem & c ) {
0175       fRho = c.Rho();
0176       fZ   = c.Z();
0177       fPhi = c.Phi();
0178       return *this;
0179    }
0180 
0181    /**
0182       Exact component-by-component equality
0183    */
0184    bool operator==(const Cylindrical3D & rhs) const {
0185       return fRho == rhs.fRho && fZ == rhs.fZ && fPhi == rhs.fPhi;
0186    }
0187    bool operator!= (const Cylindrical3D & rhs) const
0188    {return !(operator==(rhs));}
0189 
0190 
0191    // ============= Compatibility section ==================
0192 
0193    // The following make this coordinate system look enough like a CLHEP
0194    // vector that an assignment member template can work with either
0195    T x() const { return X();}
0196    T y() const { return Y();}
0197    T z() const { return Z(); }
0198 
0199    // ============= Specializations for improved speed ==================
0200 
0201    // (none)
0202 
0203 #if defined(__MAKECINT__) || defined(G__DICTIONARY)
0204 
0205    // ====== Set member functions for coordinates in other systems =======
0206 
0207    void SetX(Scalar x);
0208 
0209    void SetY(Scalar y);
0210 
0211    void SetEta(Scalar eta);
0212 
0213    void SetR(Scalar r);
0214 
0215    void SetTheta(Scalar theta);
0216 
0217 #endif
0218 
0219 
0220 private:
0221    T fRho = 0;
0222    T fZ = 0;
0223    T fPhi = 0;
0224 };
0225 
0226   } // end namespace Math
0227 
0228 } // end namespace ROOT
0229 
0230 // move implementations here to avoid circle dependencies
0231 
0232 #include "Math/GenVector/Cartesian3D.h"
0233 
0234 #if defined(__MAKECINT__) || defined(G__DICTIONARY)
0235 #include "Math/GenVector/GenVector_exception.h"
0236 #include "Math/GenVector/CylindricalEta3D.h"
0237 #include "Math/GenVector/Polar3D.h"
0238 #endif
0239 
0240 namespace ROOT {
0241 
0242   namespace Math {
0243 
0244 template <class T>
0245 void Cylindrical3D<T>::SetXYZ(Scalar xx, Scalar yy, Scalar zz) {
0246    *this = Cartesian3D<Scalar>(xx, yy, zz);
0247 }
0248 
0249 #if defined(__MAKECINT__) || defined(G__DICTIONARY)
0250 
0251 
0252   // ====== Set member functions for coordinates in other systems =======
0253 
0254 
0255 
0256 template <class T>
0257 void Cylindrical3D<T>::SetX(Scalar xx) {
0258    GenVector_exception e("Cylindrical3D::SetX() is not supposed to be called");
0259    throw e;
0260    Cartesian3D<Scalar> v(*this); v.SetX(xx); *this = Cylindrical3D<Scalar>(v);
0261 }
0262 template <class T>
0263 void Cylindrical3D<T>::SetY(Scalar yy) {
0264    GenVector_exception e("Cylindrical3D::SetY() is not supposed to be called");
0265    throw e;
0266    Cartesian3D<Scalar> v(*this); v.SetY(yy); *this = Cylindrical3D<Scalar>(v);
0267 }
0268 template <class T>
0269 void Cylindrical3D<T>::SetR(Scalar r) {
0270    GenVector_exception e("Cylindrical3D::SetR() is not supposed to be called");
0271    throw e;
0272    Polar3D<Scalar> v(*this); v.SetR(r);
0273    *this = Cylindrical3D<Scalar>(v);
0274 }
0275 template <class T>
0276 void Cylindrical3D<T>::SetTheta(Scalar theta) {
0277    GenVector_exception e("Cylindrical3D::SetTheta() is not supposed to be called");
0278    throw e;
0279    Polar3D<Scalar> v(*this); v.SetTheta(theta);
0280    *this = Cylindrical3D<Scalar>(v);
0281 }
0282 template <class T>
0283 void Cylindrical3D<T>::SetEta(Scalar eta) {
0284    GenVector_exception e("Cylindrical3D::SetEta() is not supposed to be called");
0285    throw e;
0286    CylindricalEta3D<Scalar> v(*this); v.SetEta(eta);
0287    *this = Cylindrical3D<Scalar>(v);
0288 }
0289 
0290 #endif
0291 
0292   } // end namespace Math
0293 
0294 } // end namespace ROOT
0295 
0296 
0297 #endif /* ROOT_Math_GenVector_Cylindrical3D  */