OpenStructure
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
vec_mat_predicates.hh
Go to the documentation of this file.
1 //------------------------------------------------------------------------------
2 // This file is part of the OpenStructure project <www.openstructure.org>
3 //
4 // Copyright (C) 2008-2011 by the OpenStructure authors
5 //
6 // This library is free software; you can redistribute it and/or modify it under
7 // the terms of the GNU Lesser General Public License as published by the Free
8 // Software Foundation; either version 3.0 of the License, or (at your option)
9 // any later version.
10 // This library is distributed in the hope that it will be useful, but WITHOUT
11 // ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
12 // FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
13 // details.
14 //
15 // You should have received a copy of the GNU Lesser General Public License
16 // along with this library; if not, write to the Free Software Foundation, Inc.,
17 // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18 //------------------------------------------------------------------------------
19 #ifndef OST_GEOM_VEC_MAT_PREDICATES_HH
20 #define OST_GEOM_VEC_MAT_PREDICATES_HH
21 #include <boost/version.hpp>
22 #include <boost/test/unit_test.hpp>
23 #include <boost/test/floating_point_comparison.hpp>
24 #include <ost/geom/geom.hh>
25 
26 
27 /*
28  This file contains several predicates to check for equality of vectors and
29  matrices. Usage:
30 
31  BOOST_CHECK(vec2_is_close(geom::Vec2(1,2), geom::Vec2(1, 2)));
32  */
33 
34 template<class V>
35 boost::test_tools::predicate_result vec_is_close(const V& v1, const V& v2,
36  Real tolerance,
37  unsigned int dim)
38 {
39  std::string labels[]={"x","y","z","w"};
40  bool flag=true;
41  boost::test_tools::predicate_result res( false );
42 #if BOOST_VERSION<105900
43  boost::test_tools::close_at_tolerance<Real> close_test(boost::test_tools::percent_tolerance(tolerance));
44 #else
45  boost::math::fpc::close_at_tolerance<Real> close_test(boost::math::fpc::percent_tolerance(tolerance));
46 #endif
47  for(unsigned int i=0;i<dim;++i){
48  if(v1[i]==0.0){
49  if(!boost::test_tools::check_is_small(v2[i],tolerance)){
50  flag=false;
51  res.message() << "Value for " << labels[i] << " differs: ( " << v1[i] << " != " << v2[i] << " ). ";
52  }
53  }else if (v2[i]==0.0){
54  if(!boost::test_tools::check_is_small(v1[i],tolerance)){
55  flag=false;
56  res.message() << "Value for "<< labels[i] << " differs: ( " << v1[i] << " != " << v2[i] << " ). ";
57  }
58  }else{
59  if(!close_test(v1[i],v2[i])){
60  flag=false;
61  res.message() << "Value for " << labels[i] << " differs: ( " << v1[i] << " != " << v2[i] << " ). ";
62  }
63  }
64  }
65  if(flag){
66  return true;
67  }else{
68  return res;
69  }
70 }
71 
72 boost::test_tools::predicate_result vec2_is_close(const geom::Vec2& v1,
73  const geom::Vec2& v2,
74  Real tolerance=geom::EPSILON)
75 {
76  return vec_is_close<geom::Vec2>(v1,v2,tolerance,2);
77 }
78 
79 boost::test_tools::predicate_result vec3_is_close(const geom::Vec3& v1,
80  const geom::Vec3& v2,
81  Real tolerance=geom::EPSILON)
82 {
83  return vec_is_close<geom::Vec3>(v1,v2,tolerance,3);
84 }
85 
86 boost::test_tools::predicate_result vec4_is_close(const geom::Vec4& v1,
87  const geom::Vec4& v2,
88  Real tolerance=geom::EPSILON)
89 {
90  return vec_is_close<geom::Vec4>(v1,v2,tolerance,4);
91 }
92 
93 template<class M>
94 boost::test_tools::predicate_result mat_is_close(const M& m1, const M& m2,
95  Real tolerance,
96  unsigned int dim)
97 {
98  bool flag=true;
99  boost::test_tools::predicate_result res( false );
100 #if BOOST_VERSION<105900
101  boost::test_tools::close_at_tolerance<Real> close_test(boost::test_tools::percent_tolerance(tolerance));
102 #else
103  boost::math::fpc::close_at_tolerance<Real> close_test(boost::math::fpc::percent_tolerance(tolerance));
104 #endif
105  for(unsigned int i=0;i<dim;++i){
106  for(unsigned int j=0;j<dim;++j){
107  if(m1(i,j)==0.0){
108  if(!boost::test_tools::check_is_small(m2(i,j),tolerance)){
109  flag=false;
110  res.message() << "Value for (" << i << "," << j << ") differs: (" << m1(i,j) << "!=" << m2(i,j) << "). ";
111  }
112  }else if (m2(i,j)==0.0){
113  if(!boost::test_tools::check_is_small(m1(i,j),tolerance)){
114  flag=false;
115  res.message() << "Value for (" << i << "," << j << ") differs: (" << m1(i,j) << "!=" << m2(i,j) << "). ";
116  }
117  }else{
118  if(!close_test(m1(i,j),m2(i,j))){
119  flag=false;
120  res.message() << "Value for (" << i << "," << j << ") differs: (" << m1(i,j) << "!=" << m2(i,j) << "). ";
121  }
122  }
123  }
124  }
125  if(flag){
126  return true;
127  }else{
128  return res;
129  }
130 }
131 
132 boost::test_tools::predicate_result mat2_is_close(const geom::Mat2& m1,
133  const geom::Mat2& m2,
134  Real tolerance=geom::EPSILON)
135 {
136  return mat_is_close<geom::Mat2>(m1,m2,tolerance,2);
137 }
138 
139 boost::test_tools::predicate_result mat3_is_close(const geom::Mat3& m1,
140  const geom::Mat3& m2,
141  Real tolerance=geom::EPSILON)
142 {
143  return mat_is_close<geom::Mat3>(m1,m2,tolerance,3);
144 }
145 
146 boost::test_tools::predicate_result mat4_is_close(const geom::Mat4& m1,
147  const geom::Mat4& m2,
148  Real tolerance=geom::EPSILON)
149 {
150  return mat_is_close<geom::Mat4>(m1,m2,tolerance,4);
151 }
152 
153 #endif
boost::test_tools::predicate_result vec_is_close(const V &v1, const V &v2, Real tolerance, unsigned int dim)
boost::test_tools::predicate_result mat3_is_close(const geom::Mat3 &m1, const geom::Mat3 &m2, Real tolerance=geom::EPSILON)
boost::test_tools::predicate_result vec4_is_close(const geom::Vec4 &v1, const geom::Vec4 &v2, Real tolerance=geom::EPSILON)
float Real
Definition: base.hh:44
boost::test_tools::predicate_result vec2_is_close(const geom::Vec2 &v1, const geom::Vec2 &v2, Real tolerance=geom::EPSILON)
static const Real EPSILON
Definition: constants.hh:28
Three dimensional vector class, using Real precision.
Definition: vec3.hh:42
boost::test_tools::predicate_result mat4_is_close(const geom::Mat4 &m1, const geom::Mat4 &m2, Real tolerance=geom::EPSILON)
boost::test_tools::predicate_result mat_is_close(const M &m1, const M &m2, Real tolerance, unsigned int dim)
boost::test_tools::predicate_result mat2_is_close(const geom::Mat2 &m1, const geom::Mat2 &m2, Real tolerance=geom::EPSILON)
boost::test_tools::predicate_result vec3_is_close(const geom::Vec3 &v1, const geom::Vec3 &v2, Real tolerance=geom::EPSILON)