#ifndef __JBXL_CPP_T_VECTOR_H_ #define __JBXL_CPP_T_VECTOR_H_ /** トレランス付ベクトル(精度保証付き)   ノルムは自動計算する. template class DllExport TVector : public Vector template double ProportionVector(TVector v1, TVector v2, double& t); */ #include "common++.h" #include #include #include "Vector.h" #include "Tolerance.h" // namespace jbxl { #define TVECTOR TVector /** template class TVector トレランス付き3次元ベクトルの定義 */ template class DllExport TVector : public Vector { public: T t; // トレランス public: TVector(T X=0, T Y=0, T Z=0, T W=0, double N=0.) { set(X, Y, Z, W, N);} ~TVector() {} void set(T X, T Y=0, T Z=0, T W=0, double N=0.); void init() { Vector::init(); t = (T)0;} }; /** template void TVector::set(T X, T Y, T Z, T W, double N) 3次元ベクトルに値をセット. ノルムの計算有り */ template void TVector::set(T X, T Y, T Z, T W, double N) { Vector::set(X, Y, Z, N); t = W; if (N<=0.0) { Vector::n = sqrt((double)(X*X + Y*Y + Z*Z)); } } /** template double ProportionVector(TVector v1, TVector v2, double& t) ベクトルv1, v2が一直線上にあるかどうかをチェックする. v1 = c*v2 の cを返す. tには誤差が入る. */ template double ProportionVector(TVector v1, TVector v2, double& t) { double cc = 0.0; double tt = Max(v2.t, Zero_Eps); if (v2.n>=tt) cc = (v1*v2)/(v2.n*v2.n); TVector dif = v1 - cc*v2; double tolerance = Max(dif.t, Zero_Eps); if (dif.n>=tolerance) { t = 0.0; return -HUGE_VAL; } t = (v1.n*v2.t + v2.n*v1.t)/(v2.n*v2.n); // 誤差 return cc; } ///////////////////////////////////////////////////////////////////////////////////////////////////////////// // オペレータ template inline TVector operator - (const TVector a) { return TVector(-a.x, -a.y, -a.z, a.t, a.n); } template inline TVector operator + (const TVector a, const TVector b) { T xx = a.x + b.x; T yy = a.y + b.y; T zz = a.z + b.z; T tt = a.t + b.t; if (Xabs(xx)(xx, yy, zz, tt); } template inline TVector operator - (const TVector a, const TVector b) { T xx = a.x - b.x; T yy = a.y - b.y; T zz = a.z - b.z; T tt = a.t + b.t; if (Xabs(xx)(xx, yy, zz, tt); } template inline TVector operator * (const R d, const TVector a) { return TVector(a.x*(T)d, a.y*(T)d, a.z*(T)d, a.t*Xabs((T)d));} template inline TVector operator * (const TVector a, const R d) { return TVector(a.x*(T)d, a.y*(T)d, a.z*(T)d, a.t*Xabs((T)d));} template inline TVector operator / (const TVector a, const R d) { return TVector(a.x/(T)d, a.y/d, a.z/d, a.t/Xabs(d));} // Cross product 外積 template inline TVector operator ^ (const TVector a, const TVector b) { T xx = a.y*b.z - a.z*b.y; T yy = a.z*b.x - a.x*b.z; T zz = a.x*b.y - a.y*b.x; T tt = a.n*b.t + a.t*b.n; if (Xabs(xx)(xx, yy, zz, tt); } // Dot product 内積 template inline T operator * (const TVector a, const TVector b) { return (T)(a.x*b.x + a.y*b.y + a.z*b.z);} // 内積の誤差 template inline T TVectorMultiTolerance(TVector a, TVector b) { return (T)(a.n*b.t + a.t*b.n); } } // namespace #endif