10 #ifndef EIGEN_SPARSE_CWISE_BINARY_OP_H
11 #define EIGEN_SPARSE_CWISE_BINARY_OP_H
32 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
33 class CwiseBinaryOpImpl<BinaryOp, Lhs, Rhs, Sparse>
34 :
public SparseMatrixBase<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
37 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> Derived;
38 typedef SparseMatrixBase<Derived> Base;
39 EIGEN_SPARSE_PUBLIC_INTERFACE(Derived)
43 (!internal::is_same<
typename internal::traits<Lhs>::StorageKind,
44 typename internal::traits<Rhs>::StorageKind>::value)
45 || ((Lhs::Flags&
RowMajorBit) == (Rhs::Flags&RowMajorBit))),
46 THE_STORAGE_ORDER_OF_BOTH_SIDES_MUST_MATCH);
52 template<
typename BinaryOp,
typename Lhs,
typename Rhs,
typename Derived,
53 typename _LhsStorageMode =
typename traits<Lhs>::StorageKind,
54 typename _RhsStorageMode =
typename traits<Rhs>::StorageKind>
55 class sparse_cwise_binary_op_inner_iterator_selector;
63 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
64 struct binary_evaluator<CwiseBinaryOp<BinaryOp, Lhs, Rhs>, IteratorBased, IteratorBased>
65 : evaluator_base<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
68 typedef typename evaluator<Lhs>::InnerIterator LhsIterator;
69 typedef typename evaluator<Rhs>::InnerIterator RhsIterator;
70 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
71 typedef typename traits<XprType>::Scalar Scalar;
72 typedef typename XprType::StorageIndex StorageIndex;
75 class ReverseInnerIterator;
80 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval, Index outer)
81 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor)
86 EIGEN_STRONG_INLINE InnerIterator& operator++()
88 if (m_lhsIter && m_rhsIter && (m_lhsIter.index() == m_rhsIter.index()))
90 m_id = m_lhsIter.index();
91 m_value = m_functor(m_lhsIter.value(), m_rhsIter.value());
95 else if (m_lhsIter && (!m_rhsIter || (m_lhsIter.index() < m_rhsIter.index())))
97 m_id = m_lhsIter.index();
98 m_value = m_functor(m_lhsIter.value(), Scalar(0));
101 else if (m_rhsIter && (!m_lhsIter || (m_lhsIter.index() > m_rhsIter.index())))
103 m_id = m_rhsIter.index();
104 m_value = m_functor(Scalar(0), m_rhsIter.value());
115 EIGEN_STRONG_INLINE Scalar value()
const {
return m_value; }
117 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
118 EIGEN_STRONG_INLINE Index row()
const {
return Lhs::IsRowMajor ? m_lhsIter.row() : index(); }
119 EIGEN_STRONG_INLINE Index col()
const {
return Lhs::IsRowMajor ? index() : m_lhsIter.col(); }
121 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id>=0; }
124 LhsIterator m_lhsIter;
125 RhsIterator m_rhsIter;
126 const BinaryOp& m_functor;
133 CoeffReadCost = evaluator<Lhs>::CoeffReadCost + evaluator<Rhs>::CoeffReadCost + functor_traits<BinaryOp>::Cost,
134 Flags = XprType::Flags
137 explicit binary_evaluator(
const XprType& xpr)
138 : m_functor(xpr.functor()),
139 m_lhsImpl(xpr.lhs()),
142 EIGEN_INTERNAL_CHECK_COST_VALUE(functor_traits<BinaryOp>::Cost);
143 EIGEN_INTERNAL_CHECK_COST_VALUE(CoeffReadCost);
146 inline Index nonZerosEstimate()
const {
147 return m_lhsImpl.nonZerosEstimate() + m_rhsImpl.nonZerosEstimate();
151 const BinaryOp m_functor;
152 evaluator<Lhs> m_lhsImpl;
153 evaluator<Rhs> m_rhsImpl;
157 template<
typename T,
typename Lhs,
typename Rhs>
158 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs>, IteratorBased, IteratorBased>
159 : evaluator_base<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs> >
162 typedef scalar_product_op<T> BinaryOp;
163 typedef typename evaluator<Lhs>::InnerIterator LhsIterator;
164 typedef typename evaluator<Rhs>::InnerIterator RhsIterator;
165 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
166 typedef typename XprType::StorageIndex StorageIndex;
167 typedef typename traits<XprType>::Scalar Scalar;
170 class ReverseInnerIterator;
175 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval, Index outer)
176 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor)
178 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
180 if (m_lhsIter.index() < m_rhsIter.index())
187 EIGEN_STRONG_INLINE InnerIterator& operator++()
191 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
193 if (m_lhsIter.index() < m_rhsIter.index())
201 EIGEN_STRONG_INLINE Scalar value()
const {
return m_functor(m_lhsIter.value(), m_rhsIter.value()); }
203 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_lhsIter.index(); }
204 EIGEN_STRONG_INLINE Index row()
const {
return m_lhsIter.row(); }
205 EIGEN_STRONG_INLINE Index col()
const {
return m_lhsIter.col(); }
207 EIGEN_STRONG_INLINE
operator bool()
const {
return (m_lhsIter && m_rhsIter); }
210 LhsIterator m_lhsIter;
211 RhsIterator m_rhsIter;
212 const BinaryOp& m_functor;
217 CoeffReadCost = evaluator<Lhs>::CoeffReadCost + evaluator<Rhs>::CoeffReadCost + functor_traits<BinaryOp>::Cost,
218 Flags = XprType::Flags
221 explicit binary_evaluator(
const XprType& xpr)
222 : m_functor(xpr.functor()),
223 m_lhsImpl(xpr.lhs()),
226 EIGEN_INTERNAL_CHECK_COST_VALUE(functor_traits<BinaryOp>::Cost);
227 EIGEN_INTERNAL_CHECK_COST_VALUE(CoeffReadCost);
230 inline Index nonZerosEstimate()
const {
231 return (std::min)(m_lhsImpl.nonZerosEstimate(), m_rhsImpl.nonZerosEstimate());
235 const BinaryOp m_functor;
236 evaluator<Lhs> m_lhsImpl;
237 evaluator<Rhs> m_rhsImpl;
241 template<
typename T,
typename Lhs,
typename Rhs>
242 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs>, IndexBased, IteratorBased>
243 : evaluator_base<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs> >
246 typedef scalar_product_op<T> BinaryOp;
247 typedef evaluator<Lhs> LhsEvaluator;
248 typedef typename evaluator<Rhs>::InnerIterator RhsIterator;
249 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
250 typedef typename XprType::StorageIndex StorageIndex;
251 typedef typename traits<XprType>::Scalar Scalar;
254 class ReverseInnerIterator;
261 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval, Index outer)
262 : m_lhsEval(aEval.m_lhsImpl), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor), m_outer(outer)
265 EIGEN_STRONG_INLINE InnerIterator& operator++()
271 EIGEN_STRONG_INLINE Scalar value()
const
272 {
return m_functor(m_lhsEval.coeff(IsRowMajor?m_outer:m_rhsIter.index(),IsRowMajor?m_rhsIter.index():m_outer), m_rhsIter.value()); }
274 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_rhsIter.index(); }
275 EIGEN_STRONG_INLINE Index row()
const {
return m_rhsIter.row(); }
276 EIGEN_STRONG_INLINE Index col()
const {
return m_rhsIter.col(); }
278 EIGEN_STRONG_INLINE
operator bool()
const {
return m_rhsIter; }
281 const LhsEvaluator &m_lhsEval;
282 RhsIterator m_rhsIter;
283 const BinaryOp& m_functor;
289 CoeffReadCost = evaluator<Lhs>::CoeffReadCost + evaluator<Rhs>::CoeffReadCost + functor_traits<BinaryOp>::Cost,
290 Flags = XprType::Flags
293 explicit binary_evaluator(
const XprType& xpr)
294 : m_functor(xpr.functor()),
295 m_lhsImpl(xpr.lhs()),
298 EIGEN_INTERNAL_CHECK_COST_VALUE(functor_traits<BinaryOp>::Cost);
299 EIGEN_INTERNAL_CHECK_COST_VALUE(CoeffReadCost);
302 inline Index nonZerosEstimate()
const {
303 return m_rhsImpl.nonZerosEstimate();
307 const BinaryOp m_functor;
308 evaluator<Lhs> m_lhsImpl;
309 evaluator<Rhs> m_rhsImpl;
313 template<
typename T,
typename Lhs,
typename Rhs>
314 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs>, IteratorBased, IndexBased>
315 : evaluator_base<CwiseBinaryOp<scalar_product_op<T>, Lhs, Rhs> >
318 typedef scalar_product_op<T> BinaryOp;
319 typedef typename evaluator<Lhs>::InnerIterator LhsIterator;
320 typedef evaluator<Rhs> RhsEvaluator;
321 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
322 typedef typename XprType::StorageIndex StorageIndex;
323 typedef typename traits<XprType>::Scalar Scalar;
326 class ReverseInnerIterator;
333 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval, Index outer)
334 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsEval(aEval.m_rhsImpl), m_functor(aEval.m_functor), m_outer(outer)
337 EIGEN_STRONG_INLINE InnerIterator& operator++()
343 EIGEN_STRONG_INLINE Scalar value()
const
344 {
return m_functor(m_lhsIter.value(),
345 m_rhsEval.coeff(IsRowMajor?m_outer:m_lhsIter.index(),IsRowMajor?m_lhsIter.index():m_outer)); }
347 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_lhsIter.index(); }
348 EIGEN_STRONG_INLINE Index row()
const {
return m_lhsIter.row(); }
349 EIGEN_STRONG_INLINE Index col()
const {
return m_lhsIter.col(); }
351 EIGEN_STRONG_INLINE
operator bool()
const {
return m_lhsIter; }
354 LhsIterator m_lhsIter;
355 const evaluator<Rhs> &m_rhsEval;
356 const BinaryOp& m_functor;
362 CoeffReadCost = evaluator<Lhs>::CoeffReadCost + evaluator<Rhs>::CoeffReadCost + functor_traits<BinaryOp>::Cost,
363 Flags = XprType::Flags
366 explicit binary_evaluator(
const XprType& xpr)
367 : m_functor(xpr.functor()),
368 m_lhsImpl(xpr.lhs()),
371 EIGEN_INTERNAL_CHECK_COST_VALUE(functor_traits<BinaryOp>::Cost);
372 EIGEN_INTERNAL_CHECK_COST_VALUE(CoeffReadCost);
375 inline Index nonZerosEstimate()
const {
376 return m_lhsImpl.nonZerosEstimate();
380 const BinaryOp m_functor;
381 evaluator<Lhs> m_lhsImpl;
382 evaluator<Rhs> m_rhsImpl;
391 template<
typename Derived>
392 template<
typename OtherDerived>
393 EIGEN_STRONG_INLINE Derived &
394 SparseMatrixBase<Derived>::operator-=(
const SparseMatrixBase<OtherDerived> &other)
396 return derived() = derived() - other.derived();
399 template<
typename Derived>
400 template<
typename OtherDerived>
401 EIGEN_STRONG_INLINE Derived &
402 SparseMatrixBase<Derived>::operator+=(
const SparseMatrixBase<OtherDerived>& other)
404 return derived() = derived() + other.derived();
407 template<
typename Derived>
408 template<
typename OtherDerived>
409 Derived& SparseMatrixBase<Derived>::operator+=(
const DiagonalBase<OtherDerived>& other)
411 call_assignment_no_alias(derived(), other.derived(), internal::add_assign_op<Scalar>());
415 template<
typename Derived>
416 template<
typename OtherDerived>
417 Derived& SparseMatrixBase<Derived>::operator-=(
const DiagonalBase<OtherDerived>& other)
419 call_assignment_no_alias(derived(), other.derived(), internal::sub_assign_op<Scalar>());
423 template<
typename Derived>
424 template<
typename OtherDerived>
425 EIGEN_STRONG_INLINE
const typename SparseMatrixBase<Derived>::template CwiseProductDenseReturnType<OtherDerived>::Type
428 return typename CwiseProductDenseReturnType<OtherDerived>::Type(derived(), other.derived());
433 #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:24
const unsigned int RowMajorBit
Definition: Constants.h:61
Definition: Eigen_Colamd.h:54