3d/vector.hh
Go to the documentation of this file.
1 /* -*- mia-c++ -*-
2  *
3  * This file is part of MIA - a toolbox for medical image analysis
4  * Copyright (c) Leipzig, Madrid 1999-2017 Gert Wollny
5  *
6  * MIA is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 3 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with MIA; if not, see <http://www.gnu.org/licenses/>.
18  *
19  */
20 
21 #ifndef __MIA_3DVECTOR_HH
22 #define __MIA_3DVECTOR_HH 1
23 
24 #include <typeinfo>
25 #include <assert.h>
26 #include <stdexcept>
27 #include <math.h>
28 #include <complex>
29 #include <iostream>
30 #include <type_traits>
31 
32 #include <mia/core/defines.hh>
33 #include <mia/core/type_traits.hh>
35 #include <mia/3d/defines3d.hh>
36 
38 
47 template < class T >
48 class T3DVector {
49 public:
51  T x;
53  T y;
55  T z;
56 
58  typedef T value_type;
59 
61  T3DVector():x(T()),y(T()),z(T()){};
62 
64  explicit T3DVector(int dim):x(T()),y(T()),z(T()){
65  assert(dim == 3);
66  }
67 
69  T3DVector(const T3DVector<T>& other) = default;
70 
72  T3DVector<T>& operator = (const T3DVector<T>& other) = default;
73 
75  T3DVector(const T& x_,const T& y_,const T& z_):
76  x(x_),y(y_),z(z_){
77  }
78 
80  template <class in> explicit T3DVector(const T3DVector<in>& org):
81  x(T(org.x)),y(T(org.y)),z(T(org.z)){
82  }
83 
85  template <class in>
87  x=org.x; y=org.y; z=org.z;
88  return *this;
89  }
90 
92  double norm2()const{
93  return x * x + y * y + z * z;
94  }
95 
97  double product() const {
98  return x * y * z;
99  }
101  double norm()const{
102  return sqrt(norm2());
103  }
104 
106  int size() const {
107  return 3;
108  }
109 
111  void fill(T v) {
112  x = y = z = v;
113  }
114 
123  const T operator [](size_t i) const {
124  assert(i < 3);
125  switch (i) {
126  case 0:return x;
127  case 1:return y;
128  case 2:return z;
129  default:
130  throw std::logic_error("Access to vectorelement out of range");
131  }
132  }
133 
142  T& operator [](size_t i) {
143  assert(i < 3);
144  switch (i) {
145  case 0:return x;
146  case 1:return y;
147  case 2:return z;
148  default:
149  throw std::logic_error("Access to vectorelement out of range");
150  }
151  }
152 
155  x+=a.x; y+=a.y; z+=a.z;
156  return *this;
157  }
158 
161  x-=a.x; y-=a.y; z-=a.z;
162  return *this;
163  }
164 
166  T3DVector<T>& operator *=(const double a){
167  x = T(x * a); y = T(y * a); z = T(z * a);
168  return *this;
169  }
170 
173  x = T(x * a.x); y = T(y * a.y); z = T(z * a.z);
174  return *this;
175  }
176 
177 
179  T3DVector<T>& operator /=(const double a){
180  assert(a != 0.0);
181  x = T(x/ a); y =T (y / a); z = T(z / a);
182  return *this;
183  }
184 
186  return T3DVector<T>(-x, -y, -z);
187  }
188 
190  void write(std::ostream& os)const {
191  os << x << "," << y << "," << z;
192  }
193 
195  void read(std::istream& is) {
196  char c;
197 
198  T r,s,t;
199  is >> c;
200  // if we get the opening delimiter '<' then we also expect the closing '>'
201  // otherwise just read three coma separated values.
202  // could use the BOOST lexicel cast for better error handling
203  if (c == '<') {
204  is >> r;
205  is >> c;
206  if (c != ',') {
207  is.clear(std::ios::badbit);
208  return;
209  }
210  is >> s;
211  is >> c;
212  if (c != ',') {
213  is.clear(std::ios::badbit);
214  return;
215  }
216  is >> t;
217  is >> c;
218  if (c != '>') {
219  is.clear(std::ios::badbit);
220  return;
221  }
222  x = r;
223  y = s;
224  z = t;
225  }else{
226  is.putback(c);
227  is >> r;
228  is >> c;
229  if (c != ',') {
230  is.clear(std::ios::badbit);
231  return;
232  }
233  is >> s;
234  is >> c;
235  if (c != ',') {
236  is.clear(std::ios::badbit);
237  return;
238  }
239  is >> t;
240  x = r;
241  y = s;
242  z = t;
243  }
244  }
245 
247  const T3DVector<T>& xyz()const {
248  return *this;
249  }
250 
252  const T3DVector<T> xzy()const {
253  return T3DVector<T>(x,z,y);
254  }
255 
257  const T3DVector<T> yxz()const {
258  return T3DVector<T>(y,x,z);
259  }
260 
262  const T3DVector<T> yzx()const {
263  return T3DVector<T>(y,z,x);
264  }
265 
267  const T3DVector<T> zyx()const {
268  return T3DVector<T>(z,y,x);
269  }
270 
272  const T3DVector<T> zxy()const {
273  return T3DVector<T>(z,x,y);
274  }
275 
277  static T3DVector<T> _1;
278 
280  static T3DVector<T> _0;
281 
283  static const unsigned int elements;
284 };
285 
286 
288 
289  static const int vector_3d_bit = 0x40000;
290 
291  static bool is_vector3d(int type) {
292  return type & vector_3d_bit;
293  }
294 };
295 
296 template <typename T>
298  static const int value = attribute_type<T>::value | vector_3d_bit;
299 };
300 
301 
303 template <typename T>
304 struct atomic_data<T3DVector<T> > {
305  typedef T type;
306  static const int size;
307 };
308 
309 template <typename T>
310 const int atomic_data<T3DVector<T> >::size = 3;
312 
313 
321 template <typename T>
323 {
324  return T3DVector<T>(
325  a.y * b.z - b.y * a.z,
326  a.z * b.x - b.z * a.x,
327  a.x * b.y - b.x * a.y
328  );
329 }
330 
331 
333 template <class T> double fabs(const T3DVector<T>& t)
334 {
335  return t.norm();
336 }
337 
339 template <class T> double dot(const T3DVector<T>& a, const T3DVector<T>& b)
340 {
341  return a.x * b.x + a. y * b.y + a.z * b.z;
342 }
343 
344 
347 
350 
353 
354 
355 
357  template <class T>
358 std::ostream& operator << (std::ostream& os, const T3DVector<T>& v)
359 {
360  v.write(os);
361  return os;
362 }
363 
365 template <class T>
366 std::istream& operator >> (std::istream& is, T3DVector<T>& v)
367 {
368  v.read(is);
369  return is;
370 }
371 
372 
374 template <class T>
375 inline const T3DVector<T> operator +(const T3DVector<T>& a,const T3DVector<T>& b){
376  T3DVector<T> tmp(a);
377  tmp += b;
378  return tmp;
379 }
380 
389 template <typename T, typename S>
391 {
392  return T3DVector<T>(a.x + b.x, a.y + b.y, a.z + b.z);
393 }
394 
395 
397 template <class T>
398 inline const T3DVector<T> operator -(const T3DVector<T>& a,const T3DVector<T>& b){
399  T3DVector<T> tmp(a);
400  tmp -= b;
401  return tmp;
402 }
403 
405 template <class T>
406 inline const T3DVector<T> operator *(const T3DVector<T>& a,const T3DVector<T>& b)
407 {
408  return T3DVector<T>(b.x * a.x, b.y * a.y, b.z * a.z);
409 }
410 
412 template <class T>
413 inline const T3DVector<T> operator /(const T3DVector<T>& a,double f)
414 {
415  assert(f != T());
416  T3DVector<T> tmp (a);
417  tmp /= f;
418  return tmp;
419 }
420 
425 template <class T>
426 inline const T3DVector<T> operator / (const T3DVector<T>& a, const T3DVector<T>& b)
427 {
428  assert(b.x != 0.0 && b.y != 0.0 && b.z != 0.0);
429  return T3DVector<T>(a.x/b.x, a.y/b.y, a.z/b.z);
430 }
431 
432 
434 template <class T>
435 inline const T3DVector<T> operator *(const T3DVector<T>& a, double f)
436 {
437  T3DVector<T> tmp (a);
438  tmp *= f;
439  return tmp;
440 }
441 
442 
444 template <class T>
445 inline const T3DVector<T> operator *(double f, const T3DVector<T>& a)
446 {
447  return a * f;
448 }
449 
450 
452 template <class T>
453 inline const T3DVector<T> operator ^(const T3DVector<T>& a,const T3DVector<T>& b)
454 {
455  return T3DVector<T>( a.y * b.z - b.y * a.z,
456  a.z * b.x - b.z * a.x,
457  a.x * b.y - b.x * a.y);
458 }
459 
461 template <class T>
462 inline bool operator == (const T3DVector<T>& a,const T3DVector<T>& b)
463 {
464  return (b.x == a.x && b.y == a.y && b.z == a.z);
465 }
466 
468 template <class T>
469 inline bool operator != (const T3DVector<T>& a,const T3DVector<T>& b)
470 {
471  return ! (a == b);
472 }
473 
475 template <class T>
476 bool operator < (const T3DVector<T>& a,const T3DVector<T>& b){
477  return (a.x < b.x && a.y < b.y && a.z < b.z);
478 }
479 
481 template <class T>
482 bool operator <= (const T3DVector<T>& b, const T3DVector<T>& a){
483  return (b.x <= a.x && b.y <= a.y && b.z <= a.z);
484 }
485 
487 template <class T>
488 bool operator > (const T3DVector<T>& b, const T3DVector<T>& a){
489  return (b.x > a.x && b.y > a.y && b.z > a.z);
490 }
491 
493 template <class T>
494 bool operator >= (const T3DVector<T>& b, const T3DVector<T>& a){
495  return (b.x >= a.x && b.y >= a.y && b.z >= a.z);
496 }
497 template <typename T >
499 
500 template <typename T >
502 
503 template <typename T>
504 struct less_then<T3DVector<T> > {
505  bool operator() (const T3DVector<T>& a, const T3DVector<T>& b) const{
506  return a.z < b.z ||
507  (a.z == b.z &&
508  (a.y < b.y || (a.y == b.y && a.x < b.x)));
509  }
510 };
511 
512 
513 
515 
516 
517 #endif
const T3DVector< T > operator/(const T3DVector< T > &a, double f)
vector division by scalar
Definition: 3d/vector.hh:413
T3DVector< T > & operator=(const T3DVector< T > &other)=default
we provide the default copy mechanisms
const T operator[](size_t i) const
Definition: 3d/vector.hh:123
T3DVector< double > C3DDVector
A double 3D Vector.
Definition: 3d/vector.hh:349
void read(std::istream &is)
read the vector from a formatted string
Definition: 3d/vector.hh:195
T z
vector element
Definition: 3d/vector.hh:55
int size() const
Definition: 3d/vector.hh:106
double product() const
Definition: 3d/vector.hh:97
const T3DVector< T > operator+(const T3DVector< T > &a, const T3DVector< T > &b)
vector addition
Definition: 3d/vector.hh:375
double norm2() const
square of Euclidian norm of the vector
Definition: 3d/vector.hh:92
const T3DVector< T > yxz() const
swizzle operator
Definition: 3d/vector.hh:257
bool operator==(const T3DVector< T > &a, const T3DVector< T > &b)
comparison operator equal
Definition: 3d/vector.hh:462
T3DVector< float > C3DFVector
A float 3D Vector.
Definition: 3d/vector.hh:346
#define NS_MIA_BEGIN
conveniance define to start the mia namespace
Definition: defines.hh:33
T value_type
typedef for generic programming
Definition: 3d/vector.hh:58
double dot(const T3DVector< T > &a, const T3DVector< T > &b)
Definition: 3d/vector.hh:339
static T3DVector< T > _0
declare the vector (0,0,0)
Definition: 3d/vector.hh:280
T3DVector< T > & operator-=(const T3DVector< T > &a)
inplace subtraction
Definition: 3d/vector.hh:160
T3DVector< T > & operator/=(const double a)
inplace divisison by a scalar
Definition: 3d/vector.hh:179
T3DVector()
standart constructor
Definition: 3d/vector.hh:61
T3DVector< T > cross(const T3DVector< T > &a, const T3DVector< T > &b)
Definition: 3d/vector.hh:322
const T3DVector< T > & xyz() const
swizzle operator
Definition: 3d/vector.hh:247
const T3DVector< T > zxy() const
swizzle operator
Definition: 3d/vector.hh:272
std::istream & operator>>(std::istream &is, T3DVector< T > &v)
stream input operator for 3DVector
Definition: 3d/vector.hh:366
const T3DVector< T > operator*(const T3DVector< T > &a, const T3DVector< T > &b)
vector scalar product
Definition: 3d/vector.hh:406
T y
vector element
Definition: 3d/vector.hh:53
T3DVector< T > & operator*=(const double a)
inplace multiplication
Definition: 3d/vector.hh:166
static T3DVector< T > _1
declare the vector (1,1,1)
Definition: 3d/vector.hh:277
bool operator>=(const T3DVector< T > &b, const T3DVector< T > &a)
comparison greater or equal, returns true if all components of a are greater or equal then those of b...
Definition: 3d/vector.hh:494
double fabs(const T3DVector< T > &t)
A way to get the norm of a T3DVector using faba syntax.
Definition: 3d/vector.hh:333
const T3DVector< T > operator^(const T3DVector< T > &a, const T3DVector< T > &b)
3D vector cross product
Definition: 3d/vector.hh:453
void fill(T v)
Fill the vector elements with value v.
Definition: 3d/vector.hh:111
T3DVector(const T3DVector< in > &org)
type casting copy constructor
Definition: 3d/vector.hh:80
static const unsigned int elements
the number of elements this vector holds (=3)
Definition: 3d/vector.hh:283
T3DVector(const T &x_, const T &y_, const T &z_)
constructor to construct vector from values
Definition: 3d/vector.hh:75
T3DVector(int dim)
create a zero-vector, dim must be 3
Definition: 3d/vector.hh:64
T3DVector< unsigned int > C3DBounds
A unsinged int 3D Vector (used for 3D field sizes)
Definition: 3d/vector.hh:352
A simple 3D vector type.
Definition: 3d/vector.hh:48
const T3DVector< T > xzy() const
swizzle operator
Definition: 3d/vector.hh:252
T3DVector< T > & operator+=(const T3DVector< T > &a)
inplace addition
Definition: 3d/vector.hh:154
T3DVector operator-() const
Definition: 3d/vector.hh:185
const T3DVector< T > zyx() const
swizzle operator
Definition: 3d/vector.hh:267
const T3DVector< T > yzx() const
swizzle operator
Definition: 3d/vector.hh:262
bool operator>(const T3DVector< T > &b, const T3DVector< T > &a)
comparison greater, returns true if all components of a are greater then those of b ...
Definition: 3d/vector.hh:488
bool operator!=(const T3DVector< T > &a, const T3DVector< T > &b)
comparison operator not equal
Definition: 3d/vector.hh:469
T x
vector element
Definition: 3d/vector.hh:51
void write(std::ostream &os) const
print out the formatted vector to the stream
Definition: 3d/vector.hh:190
static bool is_vector3d(int type)
Definition: 3d/vector.hh:291
double norm() const
Definition: 3d/vector.hh:101
#define NS_MIA_END
conveniance define to end the mia namespace
Definition: defines.hh:36