10 #ifndef EIGEN_SPARSE_CWISE_BINARY_OP_H
11 #define EIGEN_SPARSE_CWISE_BINARY_OP_H
37 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
46 (!internal::is_same<
typename internal::traits<Lhs>::StorageKind,
47 typename internal::traits<Rhs>::StorageKind>::value)
49 THE_STORAGE_ORDER_OF_BOTH_SIDES_MUST_MATCH)
62 template<
typename XprType>
struct binary_sparse_evaluator;
64 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
66 : evaluator_base<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
69 typedef typename evaluator<Lhs>::InnerIterator
LhsIterator;
70 typedef typename evaluator<Rhs>::InnerIterator RhsIterator;
72 typedef typename traits<XprType>::Scalar Scalar;
73 typedef typename XprType::StorageIndex StorageIndex;
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), m_value(Scalar(0))
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());
114 EIGEN_STRONG_INLINE Scalar value()
const {
return m_value; }
116 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
117 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
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; }
125 RhsIterator m_rhsIter;
133 CoeffReadCost = int(evaluator<Lhs>::CoeffReadCost) + int(evaluator<Rhs>::CoeffReadCost) + int(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()),
146 inline Index nonZerosEstimate()
const {
147 return m_lhsImpl.nonZerosEstimate() + m_rhsImpl.nonZerosEstimate();
152 evaluator<Lhs> m_lhsImpl;
153 evaluator<Rhs> m_rhsImpl;
157 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
158 struct binary_evaluator<CwiseBinaryOp<
BinaryOp, Lhs, Rhs>, IndexBased, IteratorBased>
159 : evaluator_base<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
162 typedef typename evaluator<Rhs>::InnerIterator RhsIterator;
163 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
164 typedef typename traits<XprType>::Scalar Scalar;
165 typedef typename XprType::StorageIndex StorageIndex;
173 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval,
Index outer)
174 : m_lhsEval(aEval.m_lhsImpl), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor), m_value(0), m_id(-1), m_innerSize(aEval.m_expr.rhs().innerSize())
179 EIGEN_STRONG_INLINE InnerIterator&
operator++()
184 Scalar lhsVal = m_lhsEval.coeff(IsRowMajor?m_rhsIter.outer():m_id,
185 IsRowMajor?m_id:m_rhsIter.outer());
186 if(m_rhsIter && m_rhsIter.index()==m_id)
188 m_value = m_functor(lhsVal, m_rhsIter.value());
192 m_value = m_functor(lhsVal, Scalar(0));
198 EIGEN_STRONG_INLINE Scalar value()
const {
eigen_internal_assert(m_id<m_innerSize);
return m_value; }
200 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
201 EIGEN_STRONG_INLINE
Index outer()
const {
return m_rhsIter.outer(); }
202 EIGEN_STRONG_INLINE
Index row()
const {
return IsRowMajor ? m_rhsIter.outer() : m_id; }
203 EIGEN_STRONG_INLINE
Index col()
const {
return IsRowMajor ? m_id : m_rhsIter.outer(); }
205 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id<m_innerSize; }
208 const evaluator<Lhs> &m_lhsEval;
209 RhsIterator m_rhsIter;
213 StorageIndex m_innerSize;
218 CoeffReadCost = int(evaluator<Lhs>::CoeffReadCost) + int(evaluator<Rhs>::CoeffReadCost) + int(functor_traits<BinaryOp>::Cost),
219 Flags = XprType::Flags
222 explicit binary_evaluator(
const XprType& xpr)
223 : m_functor(xpr.functor()),
224 m_lhsImpl(xpr.lhs()),
225 m_rhsImpl(xpr.rhs()),
232 inline Index nonZerosEstimate()
const {
233 return m_expr.size();
238 evaluator<Lhs> m_lhsImpl;
239 evaluator<Rhs> m_rhsImpl;
240 const XprType &m_expr;
244 template<
typename BinaryOp,
typename Lhs,
typename Rhs>
245 struct binary_evaluator<CwiseBinaryOp<
BinaryOp, Lhs, Rhs>, IteratorBased, IndexBased>
246 : evaluator_base<CwiseBinaryOp<BinaryOp, Lhs, Rhs> >
249 typedef typename evaluator<Lhs>::InnerIterator
LhsIterator;
250 typedef CwiseBinaryOp<BinaryOp, Lhs, Rhs> XprType;
251 typedef typename traits<XprType>::Scalar Scalar;
252 typedef typename XprType::StorageIndex StorageIndex;
260 EIGEN_STRONG_INLINE InnerIterator(
const binary_evaluator& aEval,
Index outer)
261 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsEval(aEval.m_rhsImpl), m_functor(aEval.m_functor), m_value(0), m_id(-1), m_innerSize(aEval.m_expr.lhs().innerSize())
266 EIGEN_STRONG_INLINE InnerIterator&
operator++()
271 Scalar rhsVal = m_rhsEval.coeff(IsRowMajor?m_lhsIter.outer():m_id,
272 IsRowMajor?m_id:m_lhsIter.outer());
273 if(m_lhsIter && m_lhsIter.index()==m_id)
275 m_value = m_functor(m_lhsIter.value(), rhsVal);
285 EIGEN_STRONG_INLINE Scalar value()
const {
eigen_internal_assert(m_id<m_innerSize);
return m_value; }
287 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
288 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
289 EIGEN_STRONG_INLINE
Index row()
const {
return IsRowMajor ? m_lhsIter.outer() : m_id; }
290 EIGEN_STRONG_INLINE
Index col()
const {
return IsRowMajor ? m_id : m_lhsIter.outer(); }
292 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id<m_innerSize; }
296 const evaluator<Rhs> &m_rhsEval;
300 StorageIndex m_innerSize;
305 CoeffReadCost = int(evaluator<Lhs>::CoeffReadCost) + int(evaluator<Rhs>::CoeffReadCost) + int(functor_traits<BinaryOp>::Cost),
306 Flags = XprType::Flags
309 explicit binary_evaluator(
const XprType& xpr)
310 : m_functor(xpr.functor()),
311 m_lhsImpl(xpr.lhs()),
312 m_rhsImpl(xpr.rhs()),
319 inline Index nonZerosEstimate()
const {
320 return m_expr.size();
325 evaluator<Lhs> m_lhsImpl;
326 evaluator<Rhs> m_rhsImpl;
327 const XprType &m_expr;
331 typename LhsKind =
typename evaluator_traits<typename T::Lhs>::Kind,
332 typename RhsKind =
typename evaluator_traits<typename T::Rhs>::Kind,
333 typename LhsScalar =
typename traits<typename T::Lhs>::Scalar,
334 typename RhsScalar =
typename traits<typename T::Rhs>::Scalar>
struct sparse_conjunction_evaluator;
337 template<
typename T1,
typename T2,
typename Lhs,
typename Rhs>
338 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs>, IteratorBased, IteratorBased>
339 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> >
341 typedef CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> XprType;
342 typedef sparse_conjunction_evaluator<XprType> Base;
343 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
346 template<
typename T1,
typename T2,
typename Lhs,
typename Rhs>
347 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs>, IndexBased, IteratorBased>
348 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> >
350 typedef CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> XprType;
351 typedef sparse_conjunction_evaluator<XprType> Base;
352 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
355 template<
typename T1,
typename T2,
typename Lhs,
typename Rhs>
356 struct binary_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs>, IteratorBased, IndexBased>
357 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> >
359 typedef CwiseBinaryOp<scalar_product_op<T1,T2>, Lhs, Rhs> XprType;
360 typedef sparse_conjunction_evaluator<XprType> Base;
361 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
365 template<
typename T1,
typename T2,
typename Lhs,
typename Rhs>
366 struct binary_evaluator<CwiseBinaryOp<scalar_quotient_op<T1,T2>, Lhs, Rhs>, IteratorBased, IndexBased>
367 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_quotient_op<T1,T2>, Lhs, Rhs> >
369 typedef CwiseBinaryOp<scalar_quotient_op<T1,T2>, Lhs, Rhs> XprType;
370 typedef sparse_conjunction_evaluator<XprType> Base;
371 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
375 template<
typename Lhs,
typename Rhs>
376 struct binary_evaluator<CwiseBinaryOp<scalar_boolean_and_op<
bool>, Lhs, Rhs>, IteratorBased, IteratorBased>
377 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> >
379 typedef CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> XprType;
380 typedef sparse_conjunction_evaluator<XprType> Base;
381 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
384 template<
typename Lhs,
typename Rhs>
385 struct binary_evaluator<CwiseBinaryOp<scalar_boolean_and_op<
bool>, Lhs, Rhs>, IndexBased, IteratorBased>
386 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> >
388 typedef CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> XprType;
389 typedef sparse_conjunction_evaluator<XprType> Base;
390 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
393 template<
typename Lhs,
typename Rhs>
394 struct binary_evaluator<CwiseBinaryOp<scalar_boolean_and_op<
bool>, Lhs, Rhs>, IteratorBased, IndexBased>
395 : sparse_conjunction_evaluator<CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> >
397 typedef CwiseBinaryOp<scalar_boolean_and_op<bool>, Lhs, Rhs> XprType;
398 typedef sparse_conjunction_evaluator<XprType> Base;
399 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
410 template<
typename XprType>
411 struct sparse_conjunction_evaluator<XprType, IteratorBased, IteratorBased>
412 : evaluator_base<XprType>
415 typedef typename XprType::Functor
BinaryOp;
416 typedef typename XprType::Lhs LhsArg;
417 typedef typename XprType::Rhs RhsArg;
418 typedef typename evaluator<LhsArg>::InnerIterator
LhsIterator;
419 typedef typename evaluator<RhsArg>::InnerIterator RhsIterator;
420 typedef typename XprType::StorageIndex StorageIndex;
421 typedef typename traits<XprType>::Scalar Scalar;
428 EIGEN_STRONG_INLINE InnerIterator(
const sparse_conjunction_evaluator& aEval,
Index outer)
429 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor)
431 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
433 if (m_lhsIter.index() < m_rhsIter.index())
440 EIGEN_STRONG_INLINE InnerIterator&
operator++()
444 while (m_lhsIter && m_rhsIter && (m_lhsIter.index() != m_rhsIter.index()))
446 if (m_lhsIter.index() < m_rhsIter.index())
454 EIGEN_STRONG_INLINE Scalar value()
const {
return m_functor(m_lhsIter.value(), m_rhsIter.value()); }
456 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_lhsIter.index(); }
457 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
458 EIGEN_STRONG_INLINE
Index row()
const {
return m_lhsIter.row(); }
459 EIGEN_STRONG_INLINE
Index col()
const {
return m_lhsIter.col(); }
461 EIGEN_STRONG_INLINE
operator bool()
const {
return (m_lhsIter && m_rhsIter); }
465 RhsIterator m_rhsIter;
471 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) + int(functor_traits<BinaryOp>::Cost),
472 Flags = XprType::Flags
475 explicit sparse_conjunction_evaluator(
const XprType& xpr)
476 : m_functor(xpr.functor()),
477 m_lhsImpl(xpr.lhs()),
484 inline Index nonZerosEstimate()
const {
485 return (
std::min)(m_lhsImpl.nonZerosEstimate(), m_rhsImpl.nonZerosEstimate());
490 evaluator<LhsArg> m_lhsImpl;
491 evaluator<RhsArg> m_rhsImpl;
495 template<
typename XprType>
496 struct sparse_conjunction_evaluator<XprType, IndexBased, IteratorBased>
497 : evaluator_base<XprType>
500 typedef typename XprType::Functor
BinaryOp;
501 typedef typename XprType::Lhs LhsArg;
502 typedef typename XprType::Rhs RhsArg;
503 typedef evaluator<LhsArg> LhsEvaluator;
504 typedef typename evaluator<RhsArg>::InnerIterator RhsIterator;
505 typedef typename XprType::StorageIndex StorageIndex;
506 typedef typename traits<XprType>::Scalar Scalar;
515 EIGEN_STRONG_INLINE InnerIterator(
const sparse_conjunction_evaluator& aEval,
Index outer)
516 : m_lhsEval(aEval.m_lhsImpl), m_rhsIter(aEval.m_rhsImpl,outer), m_functor(aEval.m_functor), m_outer(outer)
519 EIGEN_STRONG_INLINE InnerIterator&
operator++()
525 EIGEN_STRONG_INLINE Scalar value()
const
526 {
return m_functor(m_lhsEval.coeff(IsRowMajor?m_outer:m_rhsIter.index(),IsRowMajor?m_rhsIter.index():m_outer), m_rhsIter.value()); }
528 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_rhsIter.index(); }
529 EIGEN_STRONG_INLINE
Index outer()
const {
return m_rhsIter.outer(); }
530 EIGEN_STRONG_INLINE
Index row()
const {
return m_rhsIter.row(); }
531 EIGEN_STRONG_INLINE
Index col()
const {
return m_rhsIter.col(); }
533 EIGEN_STRONG_INLINE
operator bool()
const {
return m_rhsIter; }
536 const LhsEvaluator &m_lhsEval;
537 RhsIterator m_rhsIter;
544 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) + int(functor_traits<BinaryOp>::Cost),
545 Flags = XprType::Flags
548 explicit sparse_conjunction_evaluator(
const XprType& xpr)
549 : m_functor(xpr.functor()),
550 m_lhsImpl(xpr.lhs()),
557 inline Index nonZerosEstimate()
const {
558 return m_rhsImpl.nonZerosEstimate();
563 evaluator<LhsArg> m_lhsImpl;
564 evaluator<RhsArg> m_rhsImpl;
568 template<
typename XprType>
569 struct sparse_conjunction_evaluator<XprType, IteratorBased, IndexBased>
570 : evaluator_base<XprType>
573 typedef typename XprType::Functor
BinaryOp;
574 typedef typename XprType::Lhs LhsArg;
575 typedef typename XprType::Rhs RhsArg;
576 typedef typename evaluator<LhsArg>::InnerIterator
LhsIterator;
577 typedef evaluator<RhsArg> RhsEvaluator;
578 typedef typename XprType::StorageIndex StorageIndex;
579 typedef typename traits<XprType>::Scalar Scalar;
588 EIGEN_STRONG_INLINE InnerIterator(
const sparse_conjunction_evaluator& aEval,
Index outer)
589 : m_lhsIter(aEval.m_lhsImpl,outer), m_rhsEval(aEval.m_rhsImpl), m_functor(aEval.m_functor), m_outer(outer)
592 EIGEN_STRONG_INLINE InnerIterator&
operator++()
598 EIGEN_STRONG_INLINE Scalar value()
const
599 {
return m_functor(m_lhsIter.value(),
600 m_rhsEval.coeff(IsRowMajor?m_outer:m_lhsIter.index(),IsRowMajor?m_lhsIter.index():m_outer)); }
602 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_lhsIter.index(); }
603 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
604 EIGEN_STRONG_INLINE
Index row()
const {
return m_lhsIter.row(); }
605 EIGEN_STRONG_INLINE
Index col()
const {
return m_lhsIter.col(); }
607 EIGEN_STRONG_INLINE
operator bool()
const {
return m_lhsIter; }
611 const evaluator<RhsArg> &m_rhsEval;
618 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) + int(functor_traits<BinaryOp>::Cost),
619 Flags = XprType::Flags
622 explicit sparse_conjunction_evaluator(
const XprType& xpr)
623 : m_functor(xpr.functor()),
624 m_lhsImpl(xpr.lhs()),
631 inline Index nonZerosEstimate()
const {
632 return m_lhsImpl.nonZerosEstimate();
637 evaluator<LhsArg> m_lhsImpl;
638 evaluator<RhsArg> m_rhsImpl;
642 typename LhsKind =
typename evaluator_traits<typename T::Lhs>::Kind,
643 typename RhsKind =
typename evaluator_traits<typename T::Rhs>::Kind,
644 typename LhsScalar =
typename traits<typename T::Lhs>::Scalar,
645 typename RhsScalar =
typename traits<typename T::Rhs>::Scalar>
struct sparse_disjunction_evaluator;
655 template <
typename XprType>
656 struct sparse_disjunction_evaluator<XprType, IteratorBased, IteratorBased> : evaluator_base<XprType> {
658 typedef typename XprType::Functor
BinaryOp;
659 typedef typename XprType::Lhs LhsArg;
660 typedef typename XprType::Rhs RhsArg;
661 typedef typename evaluator<LhsArg>::InnerIterator
LhsIterator;
662 typedef typename evaluator<RhsArg>::InnerIterator RhsIterator;
663 typedef typename XprType::StorageIndex StorageIndex;
664 typedef typename traits<XprType>::Scalar Scalar;
667 class InnerIterator {
669 EIGEN_STRONG_INLINE InnerIterator(
const sparse_disjunction_evaluator& aEval,
Index outer)
670 : m_lhsIter(aEval.m_lhsImpl, outer),
671 m_rhsIter(aEval.m_rhsImpl, outer),
672 m_functor(aEval.m_functor),
677 EIGEN_STRONG_INLINE InnerIterator&
operator++() {
678 if (m_lhsIter && m_rhsIter && (m_lhsIter.index() == m_rhsIter.index())) {
679 m_id = m_lhsIter.index();
680 m_value = m_functor(m_lhsIter.value(), m_rhsIter.value());
683 }
else if (m_lhsIter && (!m_rhsIter || (m_lhsIter.index() < m_rhsIter.index()))) {
684 m_id = m_lhsIter.index();
685 m_value = m_lhsIter.value();
687 }
else if (m_rhsIter && (!m_lhsIter || (m_lhsIter.index() > m_rhsIter.index()))) {
688 m_id = m_rhsIter.index();
689 m_value = m_rhsIter.value();
697 EIGEN_STRONG_INLINE Scalar value()
const {
return m_value; }
699 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
700 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
701 EIGEN_STRONG_INLINE
Index row()
const {
return LhsArg::IsRowMajor ? m_lhsIter.row() : index(); }
702 EIGEN_STRONG_INLINE
Index col()
const {
return LhsArg::IsRowMajor ? index() : m_lhsIter.
col(); }
704 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id >= 0; }
708 RhsIterator m_rhsIter;
715 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) +
716 int(functor_traits<BinaryOp>::Cost),
717 Flags = XprType::Flags
720 explicit sparse_disjunction_evaluator(
const XprType& xpr)
721 : m_functor(xpr.functor()), m_lhsImpl(xpr.lhs()), m_rhsImpl(xpr.rhs()) {
726 inline Index nonZerosEstimate()
const {
return m_lhsImpl.nonZerosEstimate() + m_rhsImpl.nonZerosEstimate(); }
730 evaluator<LhsArg> m_lhsImpl;
731 evaluator<RhsArg> m_rhsImpl;
735 template <
typename XprType>
736 struct sparse_disjunction_evaluator<XprType, IndexBased, IteratorBased> : evaluator_base<XprType> {
738 typedef typename XprType::Functor
BinaryOp;
739 typedef typename XprType::Lhs LhsArg;
740 typedef typename XprType::Rhs RhsArg;
741 typedef evaluator<LhsArg> LhsEvaluator;
742 typedef typename evaluator<RhsArg>::InnerIterator RhsIterator;
743 typedef typename XprType::StorageIndex StorageIndex;
744 typedef typename traits<XprType>::Scalar Scalar;
747 class InnerIterator {
751 EIGEN_STRONG_INLINE InnerIterator(
const sparse_disjunction_evaluator& aEval,
Index outer)
752 : m_lhsEval(aEval.m_lhsImpl),
753 m_rhsIter(aEval.m_rhsImpl, outer),
754 m_functor(aEval.m_functor),
757 m_innerSize(aEval.m_expr.rhs().innerSize()) {
761 EIGEN_STRONG_INLINE InnerIterator&
operator++() {
763 if (m_id < m_innerSize) {
764 Scalar lhsVal = m_lhsEval.coeff(IsRowMajor ? m_rhsIter.outer() : m_id, IsRowMajor ? m_id : m_rhsIter.outer());
765 if (m_rhsIter && m_rhsIter.index() == m_id) {
766 m_value = m_functor(lhsVal, m_rhsIter.value());
775 EIGEN_STRONG_INLINE Scalar value()
const {
780 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
781 EIGEN_STRONG_INLINE
Index outer()
const {
return m_rhsIter.outer(); }
782 EIGEN_STRONG_INLINE
Index row()
const {
return IsRowMajor ? m_rhsIter.outer() : m_id; }
783 EIGEN_STRONG_INLINE
Index col()
const {
return IsRowMajor ? m_id : m_rhsIter.outer(); }
785 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id < m_innerSize; }
788 const evaluator<LhsArg>& m_lhsEval;
789 RhsIterator m_rhsIter;
793 StorageIndex m_innerSize;
797 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) +
798 int(functor_traits<BinaryOp>::Cost),
799 Flags = XprType::Flags
802 explicit sparse_disjunction_evaluator(
const XprType& xpr)
803 : m_functor(xpr.functor()), m_lhsImpl(xpr.lhs()), m_rhsImpl(xpr.rhs()), m_expr(xpr) {
808 inline Index nonZerosEstimate()
const {
return m_expr.size(); }
812 evaluator<LhsArg> m_lhsImpl;
813 evaluator<RhsArg> m_rhsImpl;
814 const XprType& m_expr;
818 template <
typename XprType>
819 struct sparse_disjunction_evaluator<XprType, IteratorBased, IndexBased> : evaluator_base<XprType> {
821 typedef typename XprType::Functor
BinaryOp;
822 typedef typename XprType::Lhs LhsArg;
823 typedef typename XprType::Rhs RhsArg;
824 typedef typename evaluator<LhsArg>::InnerIterator
LhsIterator;
825 typedef evaluator<RhsArg> RhsEvaluator;
826 typedef typename XprType::StorageIndex StorageIndex;
827 typedef typename traits<XprType>::Scalar Scalar;
830 class InnerIterator {
834 EIGEN_STRONG_INLINE InnerIterator(
const sparse_disjunction_evaluator& aEval,
Index outer)
835 : m_lhsIter(aEval.m_lhsImpl, outer),
836 m_rhsEval(aEval.m_rhsImpl),
837 m_functor(aEval.m_functor),
840 m_innerSize(aEval.m_expr.lhs().innerSize()) {
844 EIGEN_STRONG_INLINE InnerIterator&
operator++() {
846 if (m_id < m_innerSize) {
847 Scalar rhsVal = m_rhsEval.coeff(IsRowMajor ? m_lhsIter.outer() : m_id, IsRowMajor ? m_id : m_lhsIter.outer());
848 if (m_lhsIter && m_lhsIter.index() == m_id) {
849 m_value = m_functor(m_lhsIter.value(), rhsVal);
858 EIGEN_STRONG_INLINE Scalar value()
const {
863 EIGEN_STRONG_INLINE StorageIndex index()
const {
return m_id; }
864 EIGEN_STRONG_INLINE
Index outer()
const {
return m_lhsIter.outer(); }
865 EIGEN_STRONG_INLINE
Index row()
const {
return IsRowMajor ? m_lhsIter.outer() : m_id; }
866 EIGEN_STRONG_INLINE
Index col()
const {
return IsRowMajor ? m_id : m_lhsIter.outer(); }
868 EIGEN_STRONG_INLINE
operator bool()
const {
return m_id < m_innerSize; }
872 const evaluator<RhsArg>& m_rhsEval;
876 StorageIndex m_innerSize;
880 CoeffReadCost = int(evaluator<LhsArg>::CoeffReadCost) + int(evaluator<RhsArg>::CoeffReadCost) +
881 int(functor_traits<BinaryOp>::Cost),
882 Flags = XprType::Flags
885 explicit sparse_disjunction_evaluator(
const XprType& xpr)
886 : m_functor(xpr.functor()), m_lhsImpl(xpr.lhs()), m_rhsImpl(xpr.rhs()), m_expr(xpr) {
891 inline Index nonZerosEstimate()
const {
return m_expr.size(); }
895 evaluator<LhsArg> m_lhsImpl;
896 evaluator<RhsArg> m_rhsImpl;
897 const XprType& m_expr;
901 template <
typename T1,
typename T2,
typename DupFunc,
typename Lhs,
typename Rhs>
902 struct binary_evaluator<CwiseBinaryOp<scalar_disjunction_op<DupFunc, T1, T2>, Lhs, Rhs>, IteratorBased, IteratorBased>
903 : sparse_disjunction_evaluator<CwiseBinaryOp<scalar_disjunction_op<DupFunc, T1, T2>, Lhs, Rhs> > {
904 typedef CwiseBinaryOp<scalar_disjunction_op<DupFunc, T1, T2>, Lhs, Rhs> XprType;
905 typedef sparse_disjunction_evaluator<XprType> Base;
906 explicit binary_evaluator(
const XprType& xpr) : Base(xpr) {}
914 template<
typename Derived>
915 template<
typename OtherDerived>
918 call_assignment(derived(), other.
derived(), internal::add_assign_op<Scalar,typename OtherDerived::Scalar>());
922 template<
typename Derived>
923 template<
typename OtherDerived>
930 template<
typename Derived>
931 template<
typename OtherDerived>
932 EIGEN_STRONG_INLINE Derived &
935 return derived() = derived() - other.
derived();
938 template<
typename Derived>
939 template<
typename OtherDerived>
940 EIGEN_STRONG_INLINE Derived &
943 return derived() = derived() + other.
derived();
946 template<
typename Derived>
947 template<
typename OtherDerived>
954 template<
typename Derived>
955 template<
typename OtherDerived>
962 template<
typename Derived>
963 template<
typename OtherDerived>
970 template<
typename DenseDerived,
typename SparseDerived>
977 template<
typename SparseDerived,
typename DenseDerived>
978 EIGEN_STRONG_INLINE
const CwiseBinaryOp<internal::scalar_sum_op<typename SparseDerived::Scalar,typename DenseDerived::Scalar>,
const SparseDerived,
const DenseDerived>
984 template<
typename DenseDerived,
typename SparseDerived>
985 EIGEN_STRONG_INLINE
const CwiseBinaryOp<internal::scalar_difference_op<typename DenseDerived::Scalar,typename SparseDerived::Scalar>,
const DenseDerived,
const SparseDerived>
991 template<
typename SparseDerived,
typename DenseDerived>
992 EIGEN_STRONG_INLINE
const CwiseBinaryOp<internal::scalar_difference_op<typename SparseDerived::Scalar,typename DenseDerived::Scalar>,
const SparseDerived,
const DenseDerived>
RowXpr row(Index i)
This is the const version of row(). */.
ColXpr col(Index i)
This is the const version of col().
#define eigen_internal_assert(x)
#define EIGEN_SPARSE_PUBLIC_INTERFACE(Derived)
#define EIGEN_STATIC_ASSERT(X, MSG)
#define EIGEN_INTERNAL_CHECK_COST_VALUE(C)
Eigen::Triplet< double > T
CwiseBinaryOp< BinaryOp, Lhs, Rhs > Derived
SparseMatrixBase< Derived > Base
Generic expression where a coefficient-wise binary operator is applied to two expressions.
Base class for diagonal matrices and expressions.
const Derived & derived() const
Base class for all dense matrices, vectors, and expressions.
Base class of any sparse matrices or sparse expressions.
internal::traits< Block< SparseMatrixType, BlockRows, BlockCols, true > >::Scalar Scalar
Derived & operator-=(const SparseMatrixBase< OtherDerived > &other)
Derived & operator+=(const SparseMatrixBase< OtherDerived > &other)
const CwiseProductDenseReturnType< OtherDerived >::Type cwiseProduct(const MatrixBase< OtherDerived > &other) const
const unsigned int RowMajorBit
bfloat16 operator++(bfloat16 &a)
bfloat16() min(const bfloat16 &a, const bfloat16 &b)
void call_assignment(Dst &dst, const Src &src)
EIGEN_CONSTEXPR void call_assignment_no_alias(Dst &dst, const Src &src, const Func &func)
const CwiseBinaryOp< internal::scalar_difference_op< typename DenseDerived::Scalar, typename SparseDerived::Scalar >, const DenseDerived, const SparseDerived > operator-(const MatrixBase< DenseDerived > &a, const SparseMatrixBase< SparseDerived > &b)
EIGEN_DEFAULT_DENSE_INDEX_TYPE Index
The Index type as used for the API.
const CwiseBinaryOp< internal::scalar_sum_op< typename DenseDerived::Scalar, typename SparseDerived::Scalar >, const DenseDerived, const SparseDerived > operator+(const MatrixBase< DenseDerived > &a, const SparseMatrixBase< SparseDerived > &b)