Go to the documentation of this file.00001 #ifndef GeometryVector_newBasic2DVector_h
00002 #define GeometryVector_newBasic2DVector_h
00003
00004 #include "DataFormats/GeometryVector/interface/Phi.h"
00005 #include "DataFormats/GeometryVector/interface/PreciseFloatType.h"
00006 #include "DataFormats/GeometryVector/interface/CoordinateSets.h"
00007 #include "DataFormats/Math/interface/SSEVec.h"
00008
00009
00010 #include <cmath>
00011 #include <iosfwd>
00012
00013
00014 template < class T>
00015 class Basic2DVector {
00016 public:
00017
00018 typedef T ScalarType;
00019 typedef Geom::Polar2Cartesian<T> Polar;
00020
00025 Basic2DVector() {}
00026
00028 Basic2DVector( const Basic2DVector & p) : v(p.v) {}
00029
00030 template<typename U>
00031 Basic2DVector( const Basic2DVector<U> & p) : v(p.v) {}
00032
00033
00041 template <class Other>
00042 explicit Basic2DVector( const Other& p) : v(p.x(),p.y()) {}
00043
00045 Basic2DVector( const T& x, const T& y) : v(x,y) {}
00046
00047
00048 template<typename U>
00049 Basic2DVector(mathSSE::Vec2<U> const& iv) : v(iv){}
00050 template<typename U>
00051 Basic2DVector(mathSSE::Vec4<U> const& iv) : v(iv.xy()){}
00052
00053
00055 T x() const { return v[0];}
00056
00058 T y() const { return v[1];}
00059
00061 T mag2() const { return ::dot(v,v);}
00062
00064 T mag() const { return std::sqrt( mag2());}
00065
00067 T r() const { return mag();}
00068
00073 T barePhi() const {return std::atan2(y(),x());}
00074 Geom::Phi<T> phi() const {return Geom::Phi<T>(atan2(y(),x()));}
00075
00079 Basic2DVector unit() const {
00080 T my_mag = mag();
00081 return my_mag == 0 ? *this : *this / my_mag;
00082 }
00083
00086 template <class U>
00087 Basic2DVector& operator+= ( const Basic2DVector<U>& p) {
00088 v = v + p.v;
00089 return *this;
00090 }
00091
00094 template <class U>
00095 Basic2DVector& operator-= ( const Basic2DVector<U>& p) {
00096 v = v - p.v;
00097 return *this;
00098 }
00099
00101 Basic2DVector operator-() const { return Basic2DVector(-v);}
00102
00104 Basic2DVector& operator*= ( T t) {
00105 v = v*t;
00106 return *this;
00107 }
00108
00110 Basic2DVector& operator/= ( T t) {
00111 t = T(1)/t;
00112 v = v*t;
00113 return *this;
00114 }
00115
00117 T dot( const Basic2DVector& lh) const { return ::dot(v,lh.v);}
00118
00124 template <class U>
00125 typename PreciseFloatType<T,U>::Type dot( const Basic2DVector<U>& lh) const {
00126 return Basic2DVector<typename PreciseFloatType<T,U>::Type>(*this)
00127 .dot(Basic2DVector<typename PreciseFloatType<T,U>::Type>(lh));
00128 }
00129
00131 T cross( const Basic2DVector& lh) const { return ::cross(v,lh.v);}
00132
00138 template <class U>
00139 typename PreciseFloatType<T,U>::Type cross( const Basic2DVector<U>& lh) const {
00140 return Basic2DVector<typename PreciseFloatType<T,U>::Type>(*this)
00141 .cross(Basic2DVector<typename PreciseFloatType<T,U>::Type>(lh));
00142 }
00143
00144
00145 public:
00146
00147 mathSSE::Vec2<T> v;
00148
00149 };
00150
00151
00152 namespace geometryDetails {
00153 std::ostream & print2D(std::ostream& s, double x, double y);
00154
00155 }
00156
00158 template <class T>
00159 inline std::ostream & operator<<( std::ostream& s, const Basic2DVector<T>& v) {
00160 return geometryDetails::print2D(s, v.x(),v.y());
00161 }
00162
00163
00165 template <class T>
00166 inline Basic2DVector<T>
00167 operator+( const Basic2DVector<T>& a, const Basic2DVector<T>& b) {
00168 return a.v+b.v;
00169 }
00170 template <class T>
00171 inline Basic2DVector<T>
00172 operator-( const Basic2DVector<T>& a, const Basic2DVector<T>& b) {
00173 return a.v-b.v;
00174 }
00175
00176 template <class T, class U>
00177 inline Basic2DVector<typename PreciseFloatType<T,U>::Type>
00178 operator+( const Basic2DVector<T>& a, const Basic2DVector<U>& b) {
00179 typedef Basic2DVector<typename PreciseFloatType<T,U>::Type> RT;
00180 return RT(a) + RT(b);
00181 }
00182
00183 template <class T, class U>
00184 inline Basic2DVector<typename PreciseFloatType<T,U>::Type>
00185 operator-( const Basic2DVector<T>& a, const Basic2DVector<U>& b) {
00186 typedef Basic2DVector<typename PreciseFloatType<T,U>::Type> RT;
00187 return RT(a)-RT(b);
00188 }
00189
00190
00191
00192
00193
00194 template <class T>
00195 inline T operator*( const Basic2DVector<T>& v1, const Basic2DVector<T>& v2) {
00196 return v1.dot(v2);
00197 }
00198
00200 template <class T, class U>
00201 inline typename PreciseFloatType<T,U>::Type operator*( const Basic2DVector<T>& v1,
00202 const Basic2DVector<U>& v2) {
00203 return v1.dot(v2);
00204 }
00205
00206
00210 template <class T, class Scalar>
00211 inline Basic2DVector<T> operator*( const Basic2DVector<T>& v, const Scalar& s) {
00212 T t = static_cast<T>(s);
00213 return Basic2DVector<T>(v.v*t);
00214 }
00215
00217 template <class T, class Scalar>
00218 inline Basic2DVector<T> operator*( const Scalar& s, const Basic2DVector<T>& v) {
00219 T t = static_cast<T>(s);
00220 return Basic2DVector<T>(v.v*t);
00221 }
00222
00226 template <class T, class Scalar>
00227 inline Basic2DVector<T> operator/( const Basic2DVector<T>& v, const Scalar& s) {
00228 T t = static_cast<T>(1/s);
00229 return Basic2DVector<T>(v.v*t);
00230 }
00231
00232 typedef Basic2DVector<float> Basic2DVectorF;
00233 typedef Basic2DVector<double> Basic2DVectorD;
00234
00235
00236 #endif // GeometryVector_Basic2DVector_h