ReturnByValue.h
Go to the documentation of this file.
00001 // This file is part of Eigen, a lightweight C++ template library
00002 // for linear algebra.
00003 //
00004 // Copyright (C) 2009-2010 Gael Guennebaud <gael.guennebaud@inria.fr>
00005 // Copyright (C) 2009-2010 Benoit Jacob <jacob.benoit.1@gmail.com>
00006 //
00007 // Eigen is free software; you can redistribute it and/or
00008 // modify it under the terms of the GNU Lesser General Public
00009 // License as published by the Free Software Foundation; either
00010 // version 3 of the License, or (at your option) any later version.
00011 //
00012 // Alternatively, you can redistribute it and/or
00013 // modify it under the terms of the GNU General Public License as
00014 // published by the Free Software Foundation; either version 2 of
00015 // the License, or (at your option) any later version.
00016 //
00017 // Eigen is distributed in the hope that it will be useful, but WITHOUT ANY
00018 // WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
00019 // FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License or the
00020 // GNU General Public License for more details.
00021 //
00022 // You should have received a copy of the GNU Lesser General Public
00023 // License and a copy of the GNU General Public License along with
00024 // Eigen. If not, see <http://www.gnu.org/licenses/>.
00025 
00026 #ifndef EIGEN_RETURNBYVALUE_H
00027 #define EIGEN_RETURNBYVALUE_H
00028 
00029 namespace Eigen {
00030 
00036 namespace internal {
00037 
00038 template<typename Derived>
00039 struct traits<ReturnByValue<Derived> >
00040   : public traits<typename traits<Derived>::ReturnType>
00041 {
00042   enum {
00043     // We're disabling the DirectAccess because e.g. the constructor of
00044     // the Block-with-DirectAccess expression requires to have a coeffRef method.
00045     // Also, we don't want to have to implement the stride stuff.
00046     Flags = (traits<typename traits<Derived>::ReturnType>::Flags
00047              | EvalBeforeNestingBit) & ~DirectAccessBit
00048   };
00049 };
00050 
00051 /* The ReturnByValue object doesn't even have a coeff() method.
00052  * So the only way that nesting it in an expression can work, is by evaluating it into a plain matrix.
00053  * So internal::nested always gives the plain return matrix type.
00054  *
00055  * FIXME: I don't understand why we need this specialization: isn't this taken care of by the EvalBeforeNestingBit ??
00056  */
00057 template<typename Derived,int n,typename PlainObject>
00058 struct nested<ReturnByValue<Derived>, n, PlainObject>
00059 {
00060   typedef typename traits<Derived>::ReturnType type;
00061 };
00062 
00063 } // end namespace internal
00064 
00065 template<typename Derived> class ReturnByValue
00066   : public internal::dense_xpr_base< ReturnByValue<Derived> >::type
00067 {
00068   public:
00069     typedef typename internal::traits<Derived>::ReturnType ReturnType;
00070 
00071     typedef typename internal::dense_xpr_base<ReturnByValue>::type Base;
00072     EIGEN_DENSE_PUBLIC_INTERFACE(ReturnByValue)
00073 
00074     template<typename Dest>
00075     inline void evalTo(Dest& dst) const
00076     { static_cast<const Derived*>(this)->evalTo(dst); }
00077     inline Index rows() const { return static_cast<const Derived*>(this)->rows(); }
00078     inline Index cols() const { return static_cast<const Derived*>(this)->cols(); }
00079 
00080 #ifndef EIGEN_PARSED_BY_DOXYGEN
00081 #define Unusable YOU_ARE_TRYING_TO_ACCESS_A_SINGLE_COEFFICIENT_IN_A_SPECIAL_EXPRESSION_WHERE_THAT_IS_NOT_ALLOWED_BECAUSE_THAT_WOULD_BE_INEFFICIENT
00082     class Unusable{
00083       Unusable(const Unusable&) {}
00084       Unusable& operator=(const Unusable&) {return *this;}
00085     };
00086     const Unusable& coeff(Index) const { return *reinterpret_cast<const Unusable*>(this); }
00087     const Unusable& coeff(Index,Index) const { return *reinterpret_cast<const Unusable*>(this); }
00088     Unusable& coeffRef(Index) { return *reinterpret_cast<Unusable*>(this); }
00089     Unusable& coeffRef(Index,Index) { return *reinterpret_cast<Unusable*>(this); }
00090 #endif
00091 };
00092 
00093 template<typename Derived>
00094 template<typename OtherDerived>
00095 Derived& DenseBase<Derived>::operator=(const ReturnByValue<OtherDerived>& other)
00096 {
00097   other.evalTo(derived());
00098   return derived();
00099 }
00100 
00101 } // end namespace Eigen
00102 
00103 #endif // EIGEN_RETURNBYVALUE_H