00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #ifndef EIGEN_FUZZY_H
00027 #define EIGEN_FUZZY_H
00028
00029 #ifndef EIGEN_LEGACY_COMPARES
00030
00048 template<typename Derived>
00049 template<typename OtherDerived>
00050 bool MatrixBase<Derived>::isApprox(
00051 const MatrixBase<OtherDerived>& other,
00052 typename NumTraits<Scalar>::Real prec
00053 ) const
00054 {
00055 const typename ei_nested<Derived,2>::type nested(derived());
00056 const typename ei_nested<OtherDerived,2>::type otherNested(other.derived());
00057 return (nested - otherNested).cwise().abs2().sum() <= prec * prec * std::min(nested.cwise().abs2().sum(), otherNested.cwise().abs2().sum());
00058 }
00059
00073 template<typename Derived>
00074 bool MatrixBase<Derived>::isMuchSmallerThan(
00075 const typename NumTraits<Scalar>::Real& other,
00076 typename NumTraits<Scalar>::Real prec
00077 ) const
00078 {
00079 return cwise().abs2().sum() <= prec * prec * other * other;
00080 }
00081
00092 template<typename Derived>
00093 template<typename OtherDerived>
00094 bool MatrixBase<Derived>::isMuchSmallerThan(
00095 const MatrixBase<OtherDerived>& other,
00096 typename NumTraits<Scalar>::Real prec
00097 ) const
00098 {
00099 return this->cwise().abs2().sum() <= prec * prec * other.cwise().abs2().sum();
00100 }
00101
00102 #else
00103
00104 template<typename Derived, typename OtherDerived=Derived, bool IsVector=Derived::IsVectorAtCompileTime>
00105 struct ei_fuzzy_selector;
00106
00123 template<typename Derived>
00124 template<typename OtherDerived>
00125 bool MatrixBase<Derived>::isApprox(
00126 const MatrixBase<OtherDerived>& other,
00127 typename NumTraits<Scalar>::Real prec
00128 ) const
00129 {
00130 return ei_fuzzy_selector<Derived,OtherDerived>::isApprox(derived(), other.derived(), prec);
00131 }
00132
00143 template<typename Derived>
00144 bool MatrixBase<Derived>::isMuchSmallerThan(
00145 const typename NumTraits<Scalar>::Real& other,
00146 typename NumTraits<Scalar>::Real prec
00147 ) const
00148 {
00149 return ei_fuzzy_selector<Derived>::isMuchSmallerThan(derived(), other, prec);
00150 }
00151
00162 template<typename Derived>
00163 template<typename OtherDerived>
00164 bool MatrixBase<Derived>::isMuchSmallerThan(
00165 const MatrixBase<OtherDerived>& other,
00166 typename NumTraits<Scalar>::Real prec
00167 ) const
00168 {
00169 return ei_fuzzy_selector<Derived,OtherDerived>::isMuchSmallerThan(derived(), other.derived(), prec);
00170 }
00171
00172
00173 template<typename Derived, typename OtherDerived>
00174 struct ei_fuzzy_selector<Derived,OtherDerived,true>
00175 {
00176 typedef typename Derived::RealScalar RealScalar;
00177 static bool isApprox(const Derived& self, const OtherDerived& other, RealScalar prec)
00178 {
00179 EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(Derived,OtherDerived)
00180 ei_assert(self.size() == other.size());
00181 return((self - other).squaredNorm() <= std::min(self.squaredNorm(), other.squaredNorm()) * prec * prec);
00182 }
00183 static bool isMuchSmallerThan(const Derived& self, const RealScalar& other, RealScalar prec)
00184 {
00185 return(self.squaredNorm() <= ei_abs2(other * prec));
00186 }
00187 static bool isMuchSmallerThan(const Derived& self, const OtherDerived& other, RealScalar prec)
00188 {
00189 EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(Derived,OtherDerived)
00190 ei_assert(self.size() == other.size());
00191 return(self.squaredNorm() <= other.squaredNorm() * prec * prec);
00192 }
00193 };
00194
00195 template<typename Derived, typename OtherDerived>
00196 struct ei_fuzzy_selector<Derived,OtherDerived,false>
00197 {
00198 typedef typename Derived::RealScalar RealScalar;
00199 static bool isApprox(const Derived& self, const OtherDerived& other, RealScalar prec)
00200 {
00201 EIGEN_STATIC_ASSERT_SAME_MATRIX_SIZE(Derived,OtherDerived)
00202 ei_assert(self.rows() == other.rows() && self.cols() == other.cols());
00203 typename Derived::Nested nested(self);
00204 typename OtherDerived::Nested otherNested(other);
00205 for(int i = 0; i < self.cols(); ++i)
00206 if((nested.col(i) - otherNested.col(i)).squaredNorm()
00207 > std::min(nested.col(i).squaredNorm(), otherNested.col(i).squaredNorm()) * prec * prec)
00208 return false;
00209 return true;
00210 }
00211 static bool isMuchSmallerThan(const Derived& self, const RealScalar& other, RealScalar prec)
00212 {
00213 typename Derived::Nested nested(self);
00214 for(int i = 0; i < self.cols(); ++i)
00215 if(nested.col(i).squaredNorm() > ei_abs2(other * prec))
00216 return false;
00217 return true;
00218 }
00219 static bool isMuchSmallerThan(const Derived& self, const OtherDerived& other, RealScalar prec)
00220 {
00221 EIGEN_STATIC_ASSERT_SAME_MATRIX_SIZE(Derived,OtherDerived)
00222 ei_assert(self.rows() == other.rows() && self.cols() == other.cols());
00223 typename Derived::Nested nested(self);
00224 typename OtherDerived::Nested otherNested(other);
00225 for(int i = 0; i < self.cols(); ++i)
00226 if(nested.col(i).squaredNorm() > otherNested.col(i).squaredNorm() * prec * prec)
00227 return false;
00228 return true;
00229 }
00230 };
00231
00232 #endif
00233
00234 #endif // EIGEN_FUZZY_H