Eigen  3.2.91
Dot.h
1 // This file is part of Eigen, a lightweight C++ template library
2 // for linear algebra.
3 //
4 // Copyright (C) 2006-2008, 2010 Benoit Jacob <jacob.benoit.1@gmail.com>
5 //
6 // This Source Code Form is subject to the terms of the Mozilla
7 // Public License v. 2.0. If a copy of the MPL was not distributed
8 // with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 
10 #ifndef EIGEN_DOT_H
11 #define EIGEN_DOT_H
12 
13 namespace Eigen {
14 
15 namespace internal {
16 
17 // helper function for dot(). The problem is that if we put that in the body of dot(), then upon calling dot
18 // with mismatched types, the compiler emits errors about failing to instantiate cwiseProduct BEFORE
19 // looking at the static assertions. Thus this is a trick to get better compile errors.
20 template<typename T, typename U,
21 // the NeedToTranspose condition here is taken straight from Assign.h
22  bool NeedToTranspose = T::IsVectorAtCompileTime
23  && U::IsVectorAtCompileTime
24  && ((int(T::RowsAtCompileTime) == 1 && int(U::ColsAtCompileTime) == 1)
25  | // FIXME | instead of || to please GCC 4.4.0 stupid warning "suggest parentheses around &&".
26  // revert to || as soon as not needed anymore.
27  (int(T::ColsAtCompileTime) == 1 && int(U::RowsAtCompileTime) == 1))
28 >
29 struct dot_nocheck
30 {
31  typedef typename scalar_product_traits<typename traits<T>::Scalar,typename traits<U>::Scalar>::ReturnType ResScalar;
32  EIGEN_DEVICE_FUNC
33  static inline ResScalar run(const MatrixBase<T>& a, const MatrixBase<U>& b)
34  {
35  return a.template binaryExpr<scalar_conj_product_op<typename traits<T>::Scalar,typename traits<U>::Scalar> >(b).sum();
36  }
37 };
38 
39 template<typename T, typename U>
40 struct dot_nocheck<T, U, true>
41 {
42  typedef typename scalar_product_traits<typename traits<T>::Scalar,typename traits<U>::Scalar>::ReturnType ResScalar;
43  EIGEN_DEVICE_FUNC
44  static inline ResScalar run(const MatrixBase<T>& a, const MatrixBase<U>& b)
45  {
46  return a.transpose().template binaryExpr<scalar_conj_product_op<typename traits<T>::Scalar,typename traits<U>::Scalar> >(b).sum();
47  }
48 };
49 
50 } // end namespace internal
51 
62 template<typename Derived>
63 template<typename OtherDerived>
64 EIGEN_DEVICE_FUNC
65 typename internal::scalar_product_traits<typename internal::traits<Derived>::Scalar,typename internal::traits<OtherDerived>::Scalar>::ReturnType
67 {
68  EIGEN_STATIC_ASSERT_VECTOR_ONLY(Derived)
69  EIGEN_STATIC_ASSERT_VECTOR_ONLY(OtherDerived)
70  EIGEN_STATIC_ASSERT_SAME_VECTOR_SIZE(Derived,OtherDerived)
71  typedef internal::scalar_conj_product_op<Scalar,typename OtherDerived::Scalar> func;
72  EIGEN_CHECK_BINARY_COMPATIBILIY(func,Scalar,typename OtherDerived::Scalar);
73 
74  eigen_assert(size() == other.size());
75 
76  return internal::dot_nocheck<Derived,OtherDerived>::run(*this, other);
77 }
78 
79 //---------- implementation of L2 norm and related functions ----------
80 
87 template<typename Derived>
89 {
90  return numext::real((*this).cwiseAbs2().sum());
91 }
92 
99 template<typename Derived>
101 {
102  EIGEN_USING_STD_MATH(sqrt)
103  return sqrt(squaredNorm());
104 }
105 
112 template<typename Derived>
113 inline const typename MatrixBase<Derived>::PlainObject
115 {
116  typedef typename internal::nested_eval<Derived,2>::type _Nested;
117  _Nested n(derived());
118  return n / n.norm();
119 }
120 
127 template<typename Derived>
129 {
130  *this /= norm();
131 }
132 
133 //---------- implementation of other norms ----------
134 
135 namespace internal {
136 
137 template<typename Derived, int p>
138 struct lpNorm_selector
139 {
140  typedef typename NumTraits<typename traits<Derived>::Scalar>::Real RealScalar;
141  EIGEN_DEVICE_FUNC
142  static inline RealScalar run(const MatrixBase<Derived>& m)
143  {
144  EIGEN_USING_STD_MATH(pow)
145  return pow(m.cwiseAbs().array().pow(p).sum(), RealScalar(1)/p);
146  }
147 };
148 
149 template<typename Derived>
150 struct lpNorm_selector<Derived, 1>
151 {
152  EIGEN_DEVICE_FUNC
153  static inline typename NumTraits<typename traits<Derived>::Scalar>::Real run(const MatrixBase<Derived>& m)
154  {
155  return m.cwiseAbs().sum();
156  }
157 };
158 
159 template<typename Derived>
160 struct lpNorm_selector<Derived, 2>
161 {
162  EIGEN_DEVICE_FUNC
163  static inline typename NumTraits<typename traits<Derived>::Scalar>::Real run(const MatrixBase<Derived>& m)
164  {
165  return m.norm();
166  }
167 };
168 
169 template<typename Derived>
170 struct lpNorm_selector<Derived, Infinity>
171 {
172  EIGEN_DEVICE_FUNC
173  static inline typename NumTraits<typename traits<Derived>::Scalar>::Real run(const MatrixBase<Derived>& m)
174  {
175  return m.cwiseAbs().maxCoeff();
176  }
177 };
178 
179 } // end namespace internal
180 
187 template<typename Derived>
188 template<int p>
189 inline typename NumTraits<typename internal::traits<Derived>::Scalar>::Real
191 {
192  return internal::lpNorm_selector<Derived, p>::run(*this);
193 }
194 
195 //---------- implementation of isOrthogonal / isUnitary ----------
196 
203 template<typename Derived>
204 template<typename OtherDerived>
206 (const MatrixBase<OtherDerived>& other, const RealScalar& prec) const
207 {
208  typename internal::nested_eval<Derived,2>::type nested(derived());
209  typename internal::nested_eval<OtherDerived,2>::type otherNested(other.derived());
210  return numext::abs2(nested.dot(otherNested)) <= prec * prec * nested.squaredNorm() * otherNested.squaredNorm();
211 }
212 
224 template<typename Derived>
225 bool MatrixBase<Derived>::isUnitary(const RealScalar& prec) const
226 {
227  typename internal::nested_eval<Derived,1>::type self(derived());
228  for(Index i = 0; i < cols(); ++i)
229  {
230  if(!internal::isApprox(self.col(i).squaredNorm(), static_cast<RealScalar>(1), prec))
231  return false;
232  for(Index j = 0; j < i; ++j)
233  if(!internal::isMuchSmallerThan(self.col(i).dot(self.col(j)), static_cast<Scalar>(1), prec))
234  return false;
235  }
236  return true;
237 }
238 
239 } // end namespace Eigen
240 
241 #endif // EIGEN_DOT_H
const CwiseAbsReturnType cwiseAbs() const
Definition: MatrixBase.h:29
internal::traits< Derived >::Scalar Scalar
Definition: DenseBase.h:72
Definition: LDLT.h:16
Holds information about the various numeric (i.e. scalar) types allowed by Eigen. ...
Definition: NumTraits.h:107
void normalize()
Definition: Dot.h:128
RealScalar squaredNorm() const
Definition: Dot.h:88
const PlainObject normalized() const
Definition: Dot.h:114
Definition: Eigen_Colamd.h:54
bool isUnitary(const RealScalar &prec=NumTraits< Scalar >::dummy_precision()) const
Definition: Dot.h:225
bool isOrthogonal(const MatrixBase< OtherDerived > &other, const RealScalar &prec=NumTraits< Scalar >::dummy_precision()) const
Definition: Dot.h:206
Base class for all dense matrices, vectors, and expressions.
Definition: MatrixBase.h:48
RealScalar norm() const
Definition: Dot.h:100