+Ali3Vector Ali3Vector::GetPrimed(TRotMatrix* m) const
+{
+// Provide vector components (and errors) in a rotated frame.
+// The orientation of the rotated frame is described by the TRotMatrix
+// input argument.
+ Ali3Vector v=*this;
+ if (!m) return v;
+
+ Double_t* mat=m->GetMatrix();
+
+ Double_t a[3],aprim[3];
+
+ GetVector(a,"car");
+ aprim[0]=a[0]*mat[0]+a[1]*mat[1]+a[2]*mat[2];
+ aprim[1]=a[0]*mat[3]+a[1]*mat[4]+a[2]*mat[5];
+ aprim[2]=a[0]*mat[6]+a[1]*mat[7]+a[2]*mat[8];
+ v.SetVector(aprim,"car");
+
+ GetErrors(a,"car");
+ aprim[0]=sqrt(pow(a[0]*mat[0],2)+pow(a[1]*mat[1],2)+pow(a[2]*mat[2],2));
+ aprim[1]=sqrt(pow(a[0]*mat[3],2)+pow(a[1]*mat[4],2)+pow(a[2]*mat[5],2));
+ aprim[2]=sqrt(pow(a[0]*mat[6],2)+pow(a[1]*mat[7],2)+pow(a[2]*mat[8],2));
+ v.SetErrors(aprim,"car");
+
+ return v;
+}
+///////////////////////////////////////////////////////////////////////////
+Ali3Vector Ali3Vector::GetUnprimed(TRotMatrix* m) const
+{
+// Provide original vector components (and errors) from the rotated ones.
+// The orientation of the rotated frame is described by the TRotMatrix
+// input argument.
+// So, this is the inverse of the GetPrimed() memberfunction.
+// This memberfunction makes use of the fact that the inverse of a certain
+// TRotMatrix is given by its transposed matrix.
+ Ali3Vector v=*this;
+ if (!m) return v;
+
+ Double_t* mat=m->GetMatrix();
+
+ Double_t a[3],aprim[3];
+
+ GetVector(aprim,"car");
+ a[0]=aprim[0]*mat[0]+aprim[1]*mat[3]+aprim[2]*mat[6];
+ a[1]=aprim[0]*mat[1]+aprim[1]*mat[4]+aprim[2]*mat[7];
+ a[2]=aprim[0]*mat[2]+aprim[1]*mat[5]+aprim[2]*mat[8];
+ v.SetVector(a,"car");
+
+ GetErrors(aprim,"car");
+ a[0]=sqrt(pow(aprim[0]*mat[0],2)+pow(aprim[1]*mat[3],2)+pow(aprim[2]*mat[6],2));
+ a[1]=sqrt(pow(aprim[0]*mat[1],2)+pow(aprim[1]*mat[4],2)+pow(aprim[2]*mat[7],2));
+ a[2]=sqrt(pow(aprim[0]*mat[2],2)+pow(aprim[1]*mat[5],2)+pow(aprim[2]*mat[8],2));
+ v.SetErrors(a,"car");
+
+ return v;
+}
+///////////////////////////////////////////////////////////////////////////
+Double_t Ali3Vector::GetX(Int_t i,TString f,TString u)
+{
+// Provide i-th vector component according to reference frame f.
+//
+// The string argument "u" allows to choose between different angular units
+// in case e.g. a spherical frame is selected.
+// u = "rad" : angles provided in radians
+// "deg" : angles provided in degrees
+//
+// The default is u="rad".
+//
+// The vector components are addressed via the generic x1,x2,x3 notation.
+// So, i=1 denotes the first vector component.
+// The error on the selected component can be obtained via the
+// usual GetResultError() facility.
+
+ fDresult=0;
+
+ if (i<1 || i>3) return 0;
+
+ Double_t vec[3];
+ Double_t err[3];
+ GetVector(vec,f,u);
+ GetErrors(err,f,u);
+
+ fDresult=err[i-1];
+
+ return vec[i-1];
+}
+///////////////////////////////////////////////////////////////////////////
+Double_t Ali3Vector::GetOpeningAngle(Ali3Vector& q,TString u)
+{
+// Provide the opening angle with vector q.
+// The string argument "u" allows to choose between different output units.
+// u = "rad" : opening angle provided in radians
+// "deg" : opening angle provided in degrees
+//
+// The default is u="rad".
+
+ Double_t ang=0;
+
+ if (GetNorm()<=0. || q.GetNorm()<=0.) return ang;
+
+ Double_t vec[3];
+ Double_t err[3];
+
+ Ali3Vector v1;
+ GetVector(vec,"sph");
+ GetErrors(err,"sph");
+ vec[0]=1.;
+ err[0]=0.;
+ v1.SetVector(vec,"sph");
+ v1.SetErrors(err,"sph");
+
+ Ali3Vector v2;
+ q.GetVector(vec,"sph");
+ q.GetErrors(err,"sph");
+ vec[0]=1.;
+ err[0]=0.;
+ v2.SetVector(vec,"sph");
+ v2.SetErrors(err,"sph");
+
+ Double_t x=v1.Dot(v2);
+ Double_t dx=fDresult;
+ if (x>1.) x=1;
+ if (x<-1.) x=-1;
+ ang=acos(x);
+ fDresult=0;
+ if (fabs(x)<1.-dx) fDresult=dx/sqrt(1.-x*x);
+
+ if (u == "deg")
+ {
+ Double_t pi=acos(-1.);
+ ang*=180./pi;
+ fDresult*=180./pi;
+ }
+
+ return ang;
+}
+///////////////////////////////////////////////////////////////////////////