This forum has been archived. All content is frozen. Please use KDE Discuss instead.

Assign CwiseUnaryOp object to derived Matrix class

Tags: None
(comma "," separated)
vkubicki
Registered Member
Posts
14
Karma
0
Hello everyone,

I am trying to use Eigen for a professional project. I need to provide an interface, because my employer wants to be able to switch between numerical library for testing purposes. I have created my own Matrix template class:

Code: Select all
template<typename T, int _Rows = Eigen::Dynamic, int _Cols = Eigen::Dynamic>
class Matrix : public Eigen::Matrix<T, _Rows, _Cols>


Following the Eigen documentation, I implemented:

Code: Select all
template<typename OtherDerived>
Matrix& operator=(const Eigen::MatrixBase<OtherDerived>& other)
{
  this->Eigen::Matrix<T, _Rows, _Cols>::operator=(other);
  return *this;
};


to be able to assign Eigen objects to my new class. I also need to blend specific element-wise operations with matrix-wide operation. So I added this method to my Matrix class:

Code: Select all
/** Element-wise log computation */
const Eigen::CwiseUnaryOp<Eigen::internal::scalar_log_op<T>, const Eigen::ArrayWrapper<Eigen::Matrix<T,  _Rows, _Cols> > > log()
{
  return this->Eigen::Matrix<T, _Rows, _Cols>::array().log();
}


My problem is that I can not assign the object returned by this function to my Matrix class. Since Eigen::Matrix can by assigned this kind of object, I thought that adding:

Code: Select all
template<typename OtherDerived>
Matrix& operator=(const Eigen::EigenBase<OtherDerived>& other)
{
  this->Eigen::Matrix<T, _Rows, _Cols>::Base::operator=(other);
}


would do, but the following code:

Code: Select all
Matrix<Real> m3(3, 3);
Matrix<Real> m4(2, 2);
m3 = Matrix<Real>::Constant(3, 3, 12.);
m4 = m3.log();


while compiling, gets me the following error at runtime: "terminate called after throwing an instance of 'std::bad_alloc'"

Could you help implementing this operation into my Matrix class ?
vkubicki
Registered Member
Posts
14
Karma
0
I guess I should use something similar to the example provided at http://eigen.tuxfamily.org/dox/TopicCustomizingEigen.html:

Code: Select all
const CwiseUnaryOp<internal::scalar_add_op<Scalar>, Derived>
operator+(const Scalar& scalar) const
{ return CwiseUnaryOp<internal::scalar_add_op<Scalar>, Derived>(derived(), internal::scalar_add_op<Scalar>(scalar)); }


Maybe I should re post after more tinkering ...
User avatar
ggael
Moderator
Posts
3447
Karma
19
OS
yes, adding the extended API to MatrixBase/ArrayBase/DenseBase/etc through Eigen's plugin mechanism is the way to go.
vkubicki
Registered Member
Posts
14
Karma
0
I implemented it using:

Code: Select all
/** Element-wise log computation */
const Eigen::CwiseUnaryOp<Eigen::internal::scalar_log_op<T>,
                          const Eigen::Matrix<T, _Rows, _Cols> >
log() const
{
  return Eigen::CwiseUnaryOp<Eigen::internal::scalar_log_op<T>,
                             const Eigen::Matrix<T, _Rows, _Cols> >(this->derived(),
                                                                    Eigen::internal::scalar_log_op<T>());
}


Bookmarks



Who is online

Registered users: Bing [Bot], Google [Bot], Yahoo [Bot]