1 // This file is part of Eigen, a lightweight C++ template library 2 // for linear algebra. 3 // 4 // Copyright (C) 2007-2010 Benoit Jacob <jacob.benoit.1 (at) gmail.com> 5 // Copyright (C) 2008-2010 Gael Guennebaud <gael.guennebaud (at) inria.fr> 6 // 7 // This Source Code Form is subject to the terms of the Mozilla 8 // Public License v. 2.0. If a copy of the MPL was not distributed 9 // with this file, You can obtain one at http://mozilla.org/MPL/2.0/. 10 11 #ifndef EIGEN_DENSEBASE_H 12 #define EIGEN_DENSEBASE_H 13 14 namespace Eigen { 15 16 namespace internal { 17 18 // The index type defined by EIGEN_DEFAULT_DENSE_INDEX_TYPE must be a signed type. 19 // This dummy function simply aims at checking that at compile time. 20 static inline void check_DenseIndex_is_signed() { 21 EIGEN_STATIC_ASSERT(NumTraits<DenseIndex>::IsSigned,THE_INDEX_TYPE_MUST_BE_A_SIGNED_TYPE); 22 } 23 24 } // end namespace internal 25 26 /** \class DenseBase 27 * \ingroup Core_Module 28 * 29 * \brief Base class for all dense matrices, vectors, and arrays 30 * 31 * This class is the base that is inherited by all dense objects (matrix, vector, arrays, 32 * and related expression types). The common Eigen API for dense objects is contained in this class. 33 * 34 * \tparam Derived is the derived type, e.g., a matrix type or an expression. 35 * 36 * This class can be extended with the help of the plugin mechanism described on the page 37 * \ref TopicCustomizingEigen by defining the preprocessor symbol \c EIGEN_DENSEBASE_PLUGIN. 38 * 39 * \sa \ref TopicClassHierarchy 40 */ 41 template<typename Derived> class DenseBase 42 #ifndef EIGEN_PARSED_BY_DOXYGEN 43 : public internal::special_scalar_op_base<Derived,typename internal::traits<Derived>::Scalar, 44 typename NumTraits<typename internal::traits<Derived>::Scalar>::Real> 45 #else 46 : public DenseCoeffsBase<Derived> 47 #endif // not EIGEN_PARSED_BY_DOXYGEN 48 { 49 public: 50 using internal::special_scalar_op_base<Derived,typename internal::traits<Derived>::Scalar, 51 typename NumTraits<typename internal::traits<Derived>::Scalar>::Real>::operator*; 52 53 class InnerIterator; 54 55 typedef typename internal::traits<Derived>::StorageKind StorageKind; 56 57 /** \brief The type of indices 58 * \details To change this, \c \#define the preprocessor symbol \c EIGEN_DEFAULT_DENSE_INDEX_TYPE. 59 * \sa \ref TopicPreprocessorDirectives. 60 */ 61 typedef typename internal::traits<Derived>::Index Index; 62 63 typedef typename internal::traits<Derived>::Scalar Scalar; 64 typedef typename internal::packet_traits<Scalar>::type PacketScalar; 65 typedef typename NumTraits<Scalar>::Real RealScalar; 66 67 typedef DenseCoeffsBase<Derived> Base; 68 using Base::derived; 69 using Base::const_cast_derived; 70 using Base::rows; 71 using Base::cols; 72 using Base::size; 73 using Base::rowIndexByOuterInner; 74 using Base::colIndexByOuterInner; 75 using Base::coeff; 76 using Base::coeffByOuterInner; 77 using Base::packet; 78 using Base::packetByOuterInner; 79 using Base::writePacket; 80 using Base::writePacketByOuterInner; 81 using Base::coeffRef; 82 using Base::coeffRefByOuterInner; 83 using Base::copyCoeff; 84 using Base::copyCoeffByOuterInner; 85 using Base::copyPacket; 86 using Base::copyPacketByOuterInner; 87 using Base::operator(); 88 using Base::operator[]; 89 using Base::x; 90 using Base::y; 91 using Base::z; 92 using Base::w; 93 using Base::stride; 94 using Base::innerStride; 95 using Base::outerStride; 96 using Base::rowStride; 97 using Base::colStride; 98 typedef typename Base::CoeffReturnType CoeffReturnType; 99 100 enum { 101 102 RowsAtCompileTime = internal::traits<Derived>::RowsAtCompileTime, 103 /**< The number of rows at compile-time. This is just a copy of the value provided 104 * by the \a Derived type. If a value is not known at compile-time, 105 * it is set to the \a Dynamic constant. 106 * \sa MatrixBase::rows(), MatrixBase::cols(), ColsAtCompileTime, SizeAtCompileTime */ 107 108 ColsAtCompileTime = internal::traits<Derived>::ColsAtCompileTime, 109 /**< The number of columns at compile-time. This is just a copy of the value provided 110 * by the \a Derived type. If a value is not known at compile-time, 111 * it is set to the \a Dynamic constant. 112 * \sa MatrixBase::rows(), MatrixBase::cols(), RowsAtCompileTime, SizeAtCompileTime */ 113 114 115 SizeAtCompileTime = (internal::size_at_compile_time<internal::traits<Derived>::RowsAtCompileTime, 116 internal::traits<Derived>::ColsAtCompileTime>::ret), 117 /**< This is equal to the number of coefficients, i.e. the number of 118 * rows times the number of columns, or to \a Dynamic if this is not 119 * known at compile-time. \sa RowsAtCompileTime, ColsAtCompileTime */ 120 121 MaxRowsAtCompileTime = internal::traits<Derived>::MaxRowsAtCompileTime, 122 /**< This value is equal to the maximum possible number of rows that this expression 123 * might have. If this expression might have an arbitrarily high number of rows, 124 * this value is set to \a Dynamic. 125 * 126 * This value is useful to know when evaluating an expression, in order to determine 127 * whether it is possible to avoid doing a dynamic memory allocation. 128 * 129 * \sa RowsAtCompileTime, MaxColsAtCompileTime, MaxSizeAtCompileTime 130 */ 131 132 MaxColsAtCompileTime = internal::traits<Derived>::MaxColsAtCompileTime, 133 /**< This value is equal to the maximum possible number of columns that this expression 134 * might have. If this expression might have an arbitrarily high number of columns, 135 * this value is set to \a Dynamic. 136 * 137 * This value is useful to know when evaluating an expression, in order to determine 138 * whether it is possible to avoid doing a dynamic memory allocation. 139 * 140 * \sa ColsAtCompileTime, MaxRowsAtCompileTime, MaxSizeAtCompileTime 141 */ 142 143 MaxSizeAtCompileTime = (internal::size_at_compile_time<internal::traits<Derived>::MaxRowsAtCompileTime, 144 internal::traits<Derived>::MaxColsAtCompileTime>::ret), 145 /**< This value is equal to the maximum possible number of coefficients that this expression 146 * might have. If this expression might have an arbitrarily high number of coefficients, 147 * this value is set to \a Dynamic. 148 * 149 * This value is useful to know when evaluating an expression, in order to determine 150 * whether it is possible to avoid doing a dynamic memory allocation. 151 * 152 * \sa SizeAtCompileTime, MaxRowsAtCompileTime, MaxColsAtCompileTime 153 */ 154 155 IsVectorAtCompileTime = internal::traits<Derived>::MaxRowsAtCompileTime == 1 156 || internal::traits<Derived>::MaxColsAtCompileTime == 1, 157 /**< This is set to true if either the number of rows or the number of 158 * columns is known at compile-time to be equal to 1. Indeed, in that case, 159 * we are dealing with a column-vector (if there is only one column) or with 160 * a row-vector (if there is only one row). */ 161 162 Flags = internal::traits<Derived>::Flags, 163 /**< This stores expression \ref flags flags which may or may not be inherited by new expressions 164 * constructed from this one. See the \ref flags "list of flags". 165 */ 166 167 IsRowMajor = int(Flags) & RowMajorBit, /**< True if this expression has row-major storage order. */ 168 169 InnerSizeAtCompileTime = int(IsVectorAtCompileTime) ? int(SizeAtCompileTime) 170 : int(IsRowMajor) ? int(ColsAtCompileTime) : int(RowsAtCompileTime), 171 172 CoeffReadCost = internal::traits<Derived>::CoeffReadCost, 173 /**< This is a rough measure of how expensive it is to read one coefficient from 174 * this expression. 175 */ 176 177 InnerStrideAtCompileTime = internal::inner_stride_at_compile_time<Derived>::ret, 178 OuterStrideAtCompileTime = internal::outer_stride_at_compile_time<Derived>::ret 179 }; 180 181 enum { ThisConstantIsPrivateInPlainObjectBase }; 182 183 /** \returns the number of nonzero coefficients which is in practice the number 184 * of stored coefficients. */ 185 inline Index nonZeros() const { return size(); } 186 /** \returns true if either the number of rows or the number of columns is equal to 1. 187 * In other words, this function returns 188 * \code rows()==1 || cols()==1 \endcode 189 * \sa rows(), cols(), IsVectorAtCompileTime. */ 190 191 /** \returns the outer size. 192 * 193 * \note For a vector, this returns just 1. For a matrix (non-vector), this is the major dimension 194 * with respect to the \ref TopicStorageOrders "storage order", i.e., the number of columns for a 195 * column-major matrix, and the number of rows for a row-major matrix. */ 196 Index outerSize() const 197 { 198 return IsVectorAtCompileTime ? 1 199 : int(IsRowMajor) ? this->rows() : this->cols(); 200 } 201 202 /** \returns the inner size. 203 * 204 * \note For a vector, this is just the size. For a matrix (non-vector), this is the minor dimension 205 * with respect to the \ref TopicStorageOrders "storage order", i.e., the number of rows for a 206 * column-major matrix, and the number of columns for a row-major matrix. */ 207 Index innerSize() const 208 { 209 return IsVectorAtCompileTime ? this->size() 210 : int(IsRowMajor) ? this->cols() : this->rows(); 211 } 212 213 /** Only plain matrices/arrays, not expressions, may be resized; therefore the only useful resize methods are 214 * Matrix::resize() and Array::resize(). The present method only asserts that the new size equals the old size, and does 215 * nothing else. 216 */ 217 void resize(Index newSize) 218 { 219 EIGEN_ONLY_USED_FOR_DEBUG(newSize); 220 eigen_assert(newSize == this->size() 221 && "DenseBase::resize() does not actually allow to resize."); 222 } 223 /** Only plain matrices/arrays, not expressions, may be resized; therefore the only useful resize methods are 224 * Matrix::resize() and Array::resize(). The present method only asserts that the new size equals the old size, and does 225 * nothing else. 226 */ 227 void resize(Index nbRows, Index nbCols) 228 { 229 EIGEN_ONLY_USED_FOR_DEBUG(nbRows); 230 EIGEN_ONLY_USED_FOR_DEBUG(nbCols); 231 eigen_assert(nbRows == this->rows() && nbCols == this->cols() 232 && "DenseBase::resize() does not actually allow to resize."); 233 } 234 235 #ifndef EIGEN_PARSED_BY_DOXYGEN 236 237 /** \internal Represents a matrix with all coefficients equal to one another*/ 238 typedef CwiseNullaryOp<internal::scalar_constant_op<Scalar>,Derived> ConstantReturnType; 239 /** \internal Represents a vector with linearly spaced coefficients that allows sequential access only. */ 240 typedef CwiseNullaryOp<internal::linspaced_op<Scalar,false>,Derived> SequentialLinSpacedReturnType; 241 /** \internal Represents a vector with linearly spaced coefficients that allows random access. */ 242 typedef CwiseNullaryOp<internal::linspaced_op<Scalar,true>,Derived> RandomAccessLinSpacedReturnType; 243 /** \internal the return type of MatrixBase::eigenvalues() */ 244 typedef Matrix<typename NumTraits<typename internal::traits<Derived>::Scalar>::Real, internal::traits<Derived>::ColsAtCompileTime, 1> EigenvaluesReturnType; 245 246 #endif // not EIGEN_PARSED_BY_DOXYGEN 247 248 /** Copies \a other into *this. \returns a reference to *this. */ 249 template<typename OtherDerived> 250 Derived& operator=(const DenseBase<OtherDerived>& other); 251 252 /** Special case of the template operator=, in order to prevent the compiler 253 * from generating a default operator= (issue hit with g++ 4.1) 254 */ 255 Derived& operator=(const DenseBase& other); 256 257 template<typename OtherDerived> 258 Derived& operator=(const EigenBase<OtherDerived> &other); 259 260 template<typename OtherDerived> 261 Derived& operator+=(const EigenBase<OtherDerived> &other); 262 263 template<typename OtherDerived> 264 Derived& operator-=(const EigenBase<OtherDerived> &other); 265 266 template<typename OtherDerived> 267 Derived& operator=(const ReturnByValue<OtherDerived>& func); 268 269 #ifndef EIGEN_PARSED_BY_DOXYGEN 270 /** Copies \a other into *this without evaluating other. \returns a reference to *this. */ 271 template<typename OtherDerived> 272 Derived& lazyAssign(const DenseBase<OtherDerived>& other); 273 #endif // not EIGEN_PARSED_BY_DOXYGEN 274 275 CommaInitializer<Derived> operator<< (const Scalar& s); 276 277 template<unsigned int Added,unsigned int Removed> 278 const Flagged<Derived, Added, Removed> flagged() const; 279 280 template<typename OtherDerived> 281 CommaInitializer<Derived> operator<< (const DenseBase<OtherDerived>& other); 282 283 Eigen::Transpose<Derived> transpose(); 284 typedef typename internal::add_const<Transpose<const Derived> >::type ConstTransposeReturnType; 285 ConstTransposeReturnType transpose() const; 286 void transposeInPlace(); 287 #ifndef EIGEN_NO_DEBUG 288 protected: 289 template<typename OtherDerived> 290 void checkTransposeAliasing(const OtherDerived& other) const; 291 public: 292 #endif 293 294 295 static const ConstantReturnType 296 Constant(Index rows, Index cols, const Scalar& value); 297 static const ConstantReturnType 298 Constant(Index size, const Scalar& value); 299 static const ConstantReturnType 300 Constant(const Scalar& value); 301 302 static const SequentialLinSpacedReturnType 303 LinSpaced(Sequential_t, Index size, const Scalar& low, const Scalar& high); 304 static const RandomAccessLinSpacedReturnType 305 LinSpaced(Index size, const Scalar& low, const Scalar& high); 306 static const SequentialLinSpacedReturnType 307 LinSpaced(Sequential_t, const Scalar& low, const Scalar& high); 308 static const RandomAccessLinSpacedReturnType 309 LinSpaced(const Scalar& low, const Scalar& high); 310 311 template<typename CustomNullaryOp> 312 static const CwiseNullaryOp<CustomNullaryOp, Derived> 313 NullaryExpr(Index rows, Index cols, const CustomNullaryOp& func); 314 template<typename CustomNullaryOp> 315 static const CwiseNullaryOp<CustomNullaryOp, Derived> 316 NullaryExpr(Index size, const CustomNullaryOp& func); 317 template<typename CustomNullaryOp> 318 static const CwiseNullaryOp<CustomNullaryOp, Derived> 319 NullaryExpr(const CustomNullaryOp& func); 320 321 static const ConstantReturnType Zero(Index rows, Index cols); 322 static const ConstantReturnType Zero(Index size); 323 static const ConstantReturnType Zero(); 324 static const ConstantReturnType Ones(Index rows, Index cols); 325 static const ConstantReturnType Ones(Index size); 326 static const ConstantReturnType Ones(); 327 328 void fill(const Scalar& value); 329 Derived& setConstant(const Scalar& value); 330 Derived& setLinSpaced(Index size, const Scalar& low, const Scalar& high); 331 Derived& setLinSpaced(const Scalar& low, const Scalar& high); 332 Derived& setZero(); 333 Derived& setOnes(); 334 Derived& setRandom(); 335 336 template<typename OtherDerived> 337 bool isApprox(const DenseBase<OtherDerived>& other, 338 const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 339 bool isMuchSmallerThan(const RealScalar& other, 340 const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 341 template<typename OtherDerived> 342 bool isMuchSmallerThan(const DenseBase<OtherDerived>& other, 343 const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 344 345 bool isApproxToConstant(const Scalar& value, const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 346 bool isConstant(const Scalar& value, const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 347 bool isZero(const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 348 bool isOnes(const RealScalar& prec = NumTraits<Scalar>::dummy_precision()) const; 349 350 inline bool hasNaN() const; 351 inline bool allFinite() const; 352 353 inline Derived& operator*=(const Scalar& other); 354 inline Derived& operator/=(const Scalar& other); 355 356 typedef typename internal::add_const_on_value_type<typename internal::eval<Derived>::type>::type EvalReturnType; 357 /** \returns the matrix or vector obtained by evaluating this expression. 358 * 359 * Notice that in the case of a plain matrix or vector (not an expression) this function just returns 360 * a const reference, in order to avoid a useless copy. 361 */ 362 EIGEN_STRONG_INLINE EvalReturnType eval() const 363 { 364 // Even though MSVC does not honor strong inlining when the return type 365 // is a dynamic matrix, we desperately need strong inlining for fixed 366 // size types on MSVC. 367 return typename internal::eval<Derived>::type(derived()); 368 } 369 370 /** swaps *this with the expression \a other. 371 * 372 */ 373 template<typename OtherDerived> 374 void swap(const DenseBase<OtherDerived>& other, 375 int = OtherDerived::ThisConstantIsPrivateInPlainObjectBase) 376 { 377 SwapWrapper<Derived>(derived()).lazyAssign(other.derived()); 378 } 379 380 /** swaps *this with the matrix or array \a other. 381 * 382 */ 383 template<typename OtherDerived> 384 void swap(PlainObjectBase<OtherDerived>& other) 385 { 386 SwapWrapper<Derived>(derived()).lazyAssign(other.derived()); 387 } 388 389 390 inline const NestByValue<Derived> nestByValue() const; 391 inline const ForceAlignedAccess<Derived> forceAlignedAccess() const; 392 inline ForceAlignedAccess<Derived> forceAlignedAccess(); 393 template<bool Enable> inline const typename internal::conditional<Enable,ForceAlignedAccess<Derived>,Derived&>::type forceAlignedAccessIf() const; 394 template<bool Enable> inline typename internal::conditional<Enable,ForceAlignedAccess<Derived>,Derived&>::type forceAlignedAccessIf(); 395 396 Scalar sum() const; 397 Scalar mean() const; 398 Scalar trace() const; 399 400 Scalar prod() const; 401 402 typename internal::traits<Derived>::Scalar minCoeff() const; 403 typename internal::traits<Derived>::Scalar maxCoeff() const; 404 405 template<typename IndexType> 406 typename internal::traits<Derived>::Scalar minCoeff(IndexType* row, IndexType* col) const; 407 template<typename IndexType> 408 typename internal::traits<Derived>::Scalar maxCoeff(IndexType* row, IndexType* col) const; 409 template<typename IndexType> 410 typename internal::traits<Derived>::Scalar minCoeff(IndexType* index) const; 411 template<typename IndexType> 412 typename internal::traits<Derived>::Scalar maxCoeff(IndexType* index) const; 413 414 template<typename BinaryOp> 415 typename internal::result_of<BinaryOp(typename internal::traits<Derived>::Scalar)>::type 416 redux(const BinaryOp& func) const; 417 418 template<typename Visitor> 419 void visit(Visitor& func) const; 420 421 inline const WithFormat<Derived> format(const IOFormat& fmt) const; 422 423 /** \returns the unique coefficient of a 1x1 expression */ 424 CoeffReturnType value() const 425 { 426 EIGEN_STATIC_ASSERT_SIZE_1x1(Derived) 427 eigen_assert(this->rows() == 1 && this->cols() == 1); 428 return derived().coeff(0,0); 429 } 430 431 bool all(void) const; 432 bool any(void) const; 433 Index count() const; 434 435 typedef VectorwiseOp<Derived, Horizontal> RowwiseReturnType; 436 typedef const VectorwiseOp<const Derived, Horizontal> ConstRowwiseReturnType; 437 typedef VectorwiseOp<Derived, Vertical> ColwiseReturnType; 438 typedef const VectorwiseOp<const Derived, Vertical> ConstColwiseReturnType; 439 440 ConstRowwiseReturnType rowwise() const; 441 RowwiseReturnType rowwise(); 442 ConstColwiseReturnType colwise() const; 443 ColwiseReturnType colwise(); 444 445 static const CwiseNullaryOp<internal::scalar_random_op<Scalar>,Derived> Random(Index rows, Index cols); 446 static const CwiseNullaryOp<internal::scalar_random_op<Scalar>,Derived> Random(Index size); 447 static const CwiseNullaryOp<internal::scalar_random_op<Scalar>,Derived> Random(); 448 449 template<typename ThenDerived,typename ElseDerived> 450 const Select<Derived,ThenDerived,ElseDerived> 451 select(const DenseBase<ThenDerived>& thenMatrix, 452 const DenseBase<ElseDerived>& elseMatrix) const; 453 454 template<typename ThenDerived> 455 inline const Select<Derived,ThenDerived, typename ThenDerived::ConstantReturnType> 456 select(const DenseBase<ThenDerived>& thenMatrix, const typename ThenDerived::Scalar& elseScalar) const; 457 458 template<typename ElseDerived> 459 inline const Select<Derived, typename ElseDerived::ConstantReturnType, ElseDerived > 460 select(const typename ElseDerived::Scalar& thenScalar, const DenseBase<ElseDerived>& elseMatrix) const; 461 462 template<int p> RealScalar lpNorm() const; 463 464 template<int RowFactor, int ColFactor> 465 inline const Replicate<Derived,RowFactor,ColFactor> replicate() const; 466 467 typedef Replicate<Derived,Dynamic,Dynamic> ReplicateReturnType; 468 inline const ReplicateReturnType replicate(Index rowFacor,Index colFactor) const; 469 470 typedef Reverse<Derived, BothDirections> ReverseReturnType; 471 typedef const Reverse<const Derived, BothDirections> ConstReverseReturnType; 472 ReverseReturnType reverse(); 473 ConstReverseReturnType reverse() const; 474 void reverseInPlace(); 475 476 #define EIGEN_CURRENT_STORAGE_BASE_CLASS Eigen::DenseBase 477 # include "../plugins/BlockMethods.h" 478 # ifdef EIGEN_DENSEBASE_PLUGIN 479 # include EIGEN_DENSEBASE_PLUGIN 480 # endif 481 #undef EIGEN_CURRENT_STORAGE_BASE_CLASS 482 483 #ifdef EIGEN2_SUPPORT 484 485 Block<Derived> corner(CornerType type, Index cRows, Index cCols); 486 const Block<Derived> corner(CornerType type, Index cRows, Index cCols) const; 487 template<int CRows, int CCols> 488 Block<Derived, CRows, CCols> corner(CornerType type); 489 template<int CRows, int CCols> 490 const Block<Derived, CRows, CCols> corner(CornerType type) const; 491 492 #endif // EIGEN2_SUPPORT 493 494 495 // disable the use of evalTo for dense objects with a nice compilation error 496 template<typename Dest> inline void evalTo(Dest& ) const 497 { 498 EIGEN_STATIC_ASSERT((internal::is_same<Dest,void>::value),THE_EVAL_EVALTO_FUNCTION_SHOULD_NEVER_BE_CALLED_FOR_DENSE_OBJECTS); 499 } 500 501 protected: 502 /** Default constructor. Do nothing. */ 503 DenseBase() 504 { 505 /* Just checks for self-consistency of the flags. 506 * Only do it when debugging Eigen, as this borders on paranoiac and could slow compilation down 507 */ 508 #ifdef EIGEN_INTERNAL_DEBUGGING 509 EIGEN_STATIC_ASSERT((EIGEN_IMPLIES(MaxRowsAtCompileTime==1 && MaxColsAtCompileTime!=1, int(IsRowMajor)) 510 && EIGEN_IMPLIES(MaxColsAtCompileTime==1 && MaxRowsAtCompileTime!=1, int(!IsRowMajor))), 511 INVALID_STORAGE_ORDER_FOR_THIS_VECTOR_EXPRESSION) 512 #endif 513 } 514 515 private: 516 explicit DenseBase(int); 517 DenseBase(int,int); 518 template<typename OtherDerived> explicit DenseBase(const DenseBase<OtherDerived>&); 519 }; 520 521 } // end namespace Eigen 522 523 #endif // EIGEN_DENSEBASE_H 524