10 #ifndef EIGEN_SPARSE_CWISE_BINARY_OP_H
11 #define EIGEN_SPARSE_CWISE_BINARY_OP_H
34 template<>
struct promote_storage_type<Dense,Sparse>
35 {
typedef Sparse ret; };
37 template<>
struct promote_storage_type<Sparse,Dense>
38 {
typedef Sparse ret; };
40 template<
typename BinaryOp,
typename Lhs,
typename Rhs,
typename Derived,
41 typename _LhsStorageMode =
typename traits<Lhs>::StorageKind,
42 typename _RhsStorageMode =
typename traits<Rhs>::StorageKind>
43 class sparse_cwise_binary_op_inner_iterator_selector;
47 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
48 class CwiseBinaryOpImpl<BinaryOp, Lhs, Rhs, Sparse>
49 :
public SparseMatrixBase<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
53 class ReverseInnerIterator;
54 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> Derived;
55 EIGEN_SPARSE_PUBLIC_INTERFACE(Derived)
59 (!internal::is_same<
typename internal::traits<Lhs>::StorageKind,
60 typename internal::traits<Rhs>::StorageKind>::value)
61 || ((Lhs::Flags&
RowMajorBit) == (Rhs::Flags&RowMajorBit))),
62 THE_STORAGE_ORDER_OF_BOTH_SIDES_MUST_MATCH);
66 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
67 class CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator
68 :
public internal::sparse_cwise_binary_op_inner_iterator_selector<BinaryOp,Lhs,Rhs,typename CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator>
71 typedef typename Lhs::Index Index;
72 typedef internal::sparse_cwise_binary_op_inner_iterator_selector<
73 BinaryOp,Lhs,Rhs, InnerIterator> Base;
76 EIGEN_STRONG_INLINE InnerIterator(
const CwiseBinaryOpImpl& binOp,
typename Lhs::Index outer)
77 : Base(binOp.derived(),outer)
93 template<
typename BinaryOp,
typename Lhs,
typename Rhs,
typename Derived>
94 class sparse_cwise_binary_op_inner_iterator_selector<BinaryOp, Lhs, Rhs, Derived, Sparse, Sparse>
96 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> CwiseBinaryXpr;
97 typedef typename traits<CwiseBinaryXpr>::Scalar Scalar;
98 typedef typename traits<CwiseBinaryXpr>::_LhsNested _LhsNested;
99 typedef typename traits<CwiseBinaryXpr>::_RhsNested _RhsNested;
100 typedef typename _LhsNested::InnerIterator LhsIterator;
101 typedef typename _RhsNested::InnerIterator RhsIterator;
102 typedef typename Lhs::Index Index;
106 EIGEN_STRONG_INLINE sparse_cwise_binary_op_inner_iterator_selector(
const CwiseBinaryXpr& xpr, Index outer)
107 : m_lhsIter(xpr.lhs(),outer), m_rhsIter(xpr.rhs(),outer), m_functor(xpr.functor())
112 EIGEN_STRONG_INLINE Derived& operator++()
114 if (m_lhsIter && m_rhsIter && (m_lhsIter.index() == m_rhsIter.index()))
116 m_id = m_lhsIter.index();
117 m_value = m_functor(m_lhsIter.value(), m_rhsIter.value());
121 else if (m_lhsIter && (!m_rhsIter || (m_lhsIter.index() < m_rhsIter.index())))
123 m_id = m_lhsIter.index();
124 m_value = m_functor(m_lhsIter.value(), Scalar(0));
127 else if (m_rhsIter && (!m_lhsIter || (m_lhsIter.index() > m_rhsIter.index())))
129 m_id = m_rhsIter.index();
130 m_value = m_functor(Scalar(0), m_rhsIter.value());
138 return *
static_cast<Derived*
>(
this);
141 EIGEN_STRONG_INLINE Scalar value()
const {
return m_value; }
143 EIGEN_STRONG_INLINE Index index()
const {
return m_id; }
144 EIGEN_STRONG_INLINE Index row()
const {
return Lhs::IsRowMajor ? m_lhsIter.row() : index(); }
145 EIGEN_STRONG_INLINE Index col()
const {
return Lhs::IsRowMajor ? index() : m_lhsIter.col(); }
147 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id>=0; }
150 LhsIterator m_lhsIter;
151 RhsIterator m_rhsIter;
152 const BinaryOp& m_functor;
158 template<
typename T,
typename Lhs,
typename Rhs,
typename Derived>
159 class sparse_cwise_binary_op_inner_iterator_selector<scalar_product_op<T>, Lhs, Rhs, Derived, Sparse, Sparse>
161 typedef scalar_product_op<T> BinaryFunc;
162 typedef CwiseBinaryOp<BinaryFunc, Lhs, Rhs> CwiseBinaryXpr;
163 typedef typename CwiseBinaryXpr::Scalar Scalar;
164 typedef typename traits<CwiseBinaryXpr>::_LhsNested _LhsNested;
165 typedef typename _LhsNested::InnerIterator LhsIterator;
166 typedef typename traits<CwiseBinaryXpr>::_RhsNested _RhsNested;
167 typedef typename _RhsNested::InnerIterator RhsIterator;
168 typedef typename Lhs::Index Index;
171 EIGEN_STRONG_INLINE sparse_cwise_binary_op_inner_iterator_selector(
const CwiseBinaryXpr& xpr, Index outer)
172 : m_lhsIter(xpr.lhs(),outer), m_rhsIter(xpr.rhs(),outer), m_functor(xpr.functor())
174 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
176 if (m_lhsIter.index() < m_rhsIter.index())
183 EIGEN_STRONG_INLINE Derived& operator++()
187 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
189 if (m_lhsIter.index() < m_rhsIter.index())
194 return *
static_cast<Derived*
>(
this);
197 EIGEN_STRONG_INLINE Scalar value()
const {
return m_functor(m_lhsIter.value(), m_rhsIter.value()); }
199 EIGEN_STRONG_INLINE Index index()
const {
return m_lhsIter.index(); }
200 EIGEN_STRONG_INLINE Index row()
const {
return m_lhsIter.row(); }
201 EIGEN_STRONG_INLINE Index col()
const {
return m_lhsIter.col(); }
203 EIGEN_STRONG_INLINE
operator bool()
const {
return (m_lhsIter && m_rhsIter); }
206 LhsIterator m_lhsIter;
207 RhsIterator m_rhsIter;
208 const BinaryFunc& m_functor;
212 template<
typename T,
typename Lhs,
typename Rhs,
typename Derived>
213 class sparse_cwise_binary_op_inner_iterator_selector<scalar_product_op<T>, Lhs, Rhs, Derived, Sparse, Dense>
215 typedef scalar_product_op<T> BinaryFunc;
216 typedef CwiseBinaryOp<BinaryFunc, Lhs, Rhs> CwiseBinaryXpr;
217 typedef typename CwiseBinaryXpr::Scalar Scalar;
218 typedef typename traits<CwiseBinaryXpr>::_LhsNested _LhsNested;
219 typedef typename traits<CwiseBinaryXpr>::RhsNested RhsNested;
220 typedef typename _LhsNested::InnerIterator LhsIterator;
221 typedef typename Lhs::Index Index;
225 EIGEN_STRONG_INLINE sparse_cwise_binary_op_inner_iterator_selector(
const CwiseBinaryXpr& xpr, Index outer)
226 : m_rhs(xpr.rhs()), m_lhsIter(xpr.lhs(),outer), m_functor(xpr.functor()), m_outer(outer)
229 EIGEN_STRONG_INLINE Derived& operator++()
232 return *
static_cast<Derived*
>(
this);
235 EIGEN_STRONG_INLINE Scalar value()
const
236 {
return m_functor(m_lhsIter.value(),
237 m_rhs.coeff(IsRowMajor?m_outer:m_lhsIter.index(),IsRowMajor?m_lhsIter.index():m_outer)); }
239 EIGEN_STRONG_INLINE Index index()
const {
return m_lhsIter.index(); }
240 EIGEN_STRONG_INLINE Index row()
const {
return m_lhsIter.row(); }
241 EIGEN_STRONG_INLINE Index col()
const {
return m_lhsIter.col(); }
243 EIGEN_STRONG_INLINE
operator bool()
const {
return m_lhsIter; }
247 LhsIterator m_lhsIter;
248 const BinaryFunc m_functor;
253 template<
typename T,
typename Lhs,
typename Rhs,
typename Derived>
254 class sparse_cwise_binary_op_inner_iterator_selector<scalar_product_op<T>, Lhs, Rhs, Derived, Dense, Sparse>
256 typedef scalar_product_op<T> BinaryFunc;
257 typedef CwiseBinaryOp<BinaryFunc, Lhs, Rhs> CwiseBinaryXpr;
258 typedef typename CwiseBinaryXpr::Scalar Scalar;
259 typedef typename traits<CwiseBinaryXpr>::_RhsNested _RhsNested;
260 typedef typename _RhsNested::InnerIterator RhsIterator;
261 typedef typename Lhs::Index Index;
266 EIGEN_STRONG_INLINE sparse_cwise_binary_op_inner_iterator_selector(
const CwiseBinaryXpr& xpr, Index outer)
267 : m_xpr(xpr), m_rhsIter(xpr.rhs(),outer), m_functor(xpr.functor()), m_outer(outer)
270 EIGEN_STRONG_INLINE Derived& operator++()
273 return *
static_cast<Derived*
>(
this);
276 EIGEN_STRONG_INLINE Scalar value()
const
277 {
return m_functor(m_xpr.lhs().coeff(IsRowMajor?m_outer:m_rhsIter.index(),IsRowMajor?m_rhsIter.index():m_outer), m_rhsIter.value()); }
279 EIGEN_STRONG_INLINE Index index()
const {
return m_rhsIter.index(); }
280 EIGEN_STRONG_INLINE Index row()
const {
return m_rhsIter.row(); }
281 EIGEN_STRONG_INLINE Index col()
const {
return m_rhsIter.col(); }
283 EIGEN_STRONG_INLINE
operator bool()
const {
return m_rhsIter; }
286 const CwiseBinaryXpr& m_xpr;
287 RhsIterator m_rhsIter;
288 const BinaryFunc& m_functor;
298 template<
typename Derived>
299 template<
typename OtherDerived>
300 EIGEN_STRONG_INLINE Derived &
301 SparseMatrixBase<Derived>::operator-=(
const SparseMatrixBase<OtherDerived> &other)
303 return derived() = derived() - other.derived();
306 template<
typename Derived>
307 template<
typename OtherDerived>
308 EIGEN_STRONG_INLINE Derived &
309 SparseMatrixBase<Derived>::operator+=(
const SparseMatrixBase<OtherDerived>& other)
311 return derived() = derived() + other.derived();
314 template<
typename Derived>
315 template<
typename OtherDerived>
316 EIGEN_STRONG_INLINE
const typename SparseMatrixBase<Derived>::template CwiseProductDenseReturnType<OtherDerived>::Type
319 return typename CwiseProductDenseReturnType<OtherDerived>::Type(derived(), other.derived());
324 #endif // EIGEN_SPARSE_CWISE_BINARY_OP_H
const CwiseBinaryOp< internal::scalar_product_op< typename Derived::Scalar, typename OtherDerived::Scalar >, const Derived, const OtherDerived > cwiseProduct(const Eigen::SparseMatrixBase< OtherDerived > &other) const
Definition: SparseMatrixBase.h:23
const unsigned int RowMajorBit
Definition: Constants.h:53