1 #ifndef MSP_LINAL_VECTOR_H_
2 #define MSP_LINAL_VECTOR_H_
11 Base class to provide the components of a vector. This is used so that
12 specializations with individual members can be provided in some dimensions.
14 template<typename T, unsigned N>
15 class VectorComponents
21 VectorComponents() { }
24 T &operator[](unsigned i) { return data[i]; }
25 const T &operator[](unsigned i) const { return data[i]; }
29 class VectorComponents<T, 2>
35 VectorComponents() { }
38 T &operator[](unsigned i) { return *(&x+i); }
39 const T &operator[](unsigned i) const { return *(&x+i); }
43 class VectorComponents<T, 3>
49 VectorComponents() { }
52 T &operator[](unsigned i) { return *(&x+i); }
53 const T &operator[](unsigned i) const { return *(&x+i); }
57 class VectorComponents<T, 4>
63 VectorComponents() { }
66 T &operator[](unsigned i) { return *(&x+i); }
67 const T &operator[](unsigned i) const { return *(&x+i); }
71 A general mathematical vector.
73 template<typename T, unsigned N>
74 class Vector: public VectorComponents<T, N>
83 Vector(const Vector<U, N> &);
86 Vector<T, M> slice(unsigned) const;
88 Vector &operator*=(T);
89 Vector &operator/=(T);
90 Vector &operator+=(const Vector &);
91 Vector &operator-=(const Vector &);
98 template<typename T, unsigned N>
99 inline Vector<T, N>::Vector()
101 for(unsigned i=0; i<N; ++i)
105 template<typename T, unsigned N>
106 inline Vector<T, N>::Vector(const T *d)
108 for(unsigned i=0; i<N; ++i)
112 /* The compiler won't instantiate these unless they are used. Trying to use
113 them on the wrong class results in an error. */
114 template<typename T, unsigned N>
115 inline Vector<T, N>::Vector(T x_, T y_)
117 this->VectorComponents<T, 2>::x = x_;
118 this->VectorComponents<T, 2>::y = y_;
121 template<typename T, unsigned N>
122 inline Vector<T, N>::Vector(T x_, T y_, T z_)
124 this->VectorComponents<T, 3>::x = x_;
125 this->VectorComponents<T, 3>::y = y_;
126 this->VectorComponents<T, 3>::z = z_;
129 template<typename T, unsigned N>
130 inline Vector<T, N>::Vector(T x_, T y_, T z_, T w_)
132 this->VectorComponents<T, 4>::x = x_;
133 this->VectorComponents<T, 4>::y = y_;
134 this->VectorComponents<T, 4>::z = z_;
135 this->VectorComponents<T, 4>::w = w_;
138 template<typename T, unsigned N>
140 inline Vector<T, N>::Vector(const Vector<U, N> &v)
142 for(unsigned i=0; i<N; ++i)
146 template<typename T, unsigned N>
147 inline Vector<T, N+1> compose(const Vector<T, N> &v, T s)
150 for(unsigned i=0; i<N; ++i)
156 template<typename T, unsigned N>
157 inline Vector<T, N+1> compose(T s, const Vector<T, N> &v)
160 for(unsigned i=0; i<N; ++i)
166 template<typename T, unsigned N, unsigned M>
167 inline Vector<T, N+M> compose(const Vector<T, N> &v1, const Vector<T, M> &v2)
170 for(unsigned i=0; i<N; ++i)
172 for(unsigned i=0; i<M; ++i)
177 template<typename T, unsigned N>
179 inline Vector<T, M> Vector<T, N>::slice(unsigned j) const
182 for(unsigned i=0; i<M; ++i)
187 template<typename T, unsigned N>
188 inline Vector<T, N> &Vector<T, N>::operator*=(T s)
190 for(unsigned i=0; i<N; ++i)
195 template<typename T, unsigned N>
196 inline Vector<T, N> operator*(const Vector<T, N> &v, T s)
202 template<typename T, unsigned N>
203 inline Vector<T, N> operator*(T s, const Vector<T, N> &v)
208 template<typename T, unsigned N>
209 inline Vector<T, N> &Vector<T, N>::operator/=(T s)
211 for(unsigned i=0; i<N; ++i)
216 template<typename T, unsigned N>
217 inline Vector<T, N> operator/(const Vector<T, N> &v, T s)
223 template<typename T, unsigned N>
224 inline Vector<T, N> &Vector<T, N>::operator+=(const Vector<T, N> &v)
226 for(unsigned i=0; i<N; ++i)
231 template<typename T, unsigned N>
232 inline Vector<T, N> operator+(const Vector<T, N> &v1, const Vector<T, N> &v2)
238 template<typename T, unsigned N>
239 inline Vector<T, N> &Vector<T, N>::operator-=(const Vector<T, N> &v)
241 for(unsigned i=0; i<N; ++i)
246 template<typename T, unsigned N>
247 inline Vector<T, N> operator-(const Vector<T, N> &v1, const Vector<T, N> &v2)
253 template<typename T, unsigned N>
254 inline Vector<T, N> operator-(const Vector<T, N> &v)
257 for(unsigned i=0; i<N; ++i)
262 template<typename T, unsigned N>
263 inline bool operator==(const Vector<T, N> &v, const Vector<T, N> &w)
265 for(unsigned i=0; i<N; ++i)
271 template<typename T, unsigned N>
272 inline T inner_product(const Vector<T, N> &v1, const Vector<T, N> &v2)
275 for(unsigned i=0; i<N; ++i)
280 template<typename T, unsigned N>
281 inline T Vector<T, N>::norm() const
284 return sqrt(inner_product(*this, *this));
287 template<typename T, unsigned N>
288 inline Vector<T, N> &Vector<T, N>::normalize()
290 return *this /= norm();
293 template<typename T, unsigned N>
294 inline Vector<T, N> normalize(const Vector<T, N> &v)
297 return r.normalize();
301 inline T dot(const Vector<T, 3> &v1, const Vector<T, 3> &v2)
303 return inner_product(v1, v2);
307 inline Vector<T, 3> cross(const Vector<T, 3> &v1, const Vector<T, 3> &v2)
309 return Vector<T, 3>(v1.y*v2.z-v1.z*v2.y, v1.z*v2.x-v1.x*v2.z, v1.x*v2.y-v1.y*v2.x);